Статьи Новости Контакты

25.10.2006
Анатолий Крысов

Работаем с формами в AJAX

формы и AJAX

Итак, какая задача стоит перед нами? Во-первых, нужно создать саму форму, которую будет заполнять гипотетический посетитель нашего веб-сайта. Во-вторых, необходимо написать ряд JavaScript-функций, которые будут обрабатывать форму и данные из нее, а затем посылать на сервер. И, наконец, третий момент — серверная часть, которая в нашем случае будет написана на PHP. Разумеется, для упрощения мы сделаем серверную часть максимально короткой, а с расширением ее при желании проблем возникнуть точно не должно.

Кроме того, в JavaScript-код мы добавим функциональность для базовой проверки, которая, к примеру, позволит скрипту определять, были ли заполнены обязательные для заполнения поля. Сей механизм завязан на различных типах элементов формы, поэтому теоретически и практически с таким подходом разработчик может выбирать для текстового поля либо radio button или любого другого элемента различные виды обработки и так далее. И самое важное — полное разделение всех логик решения, что позволит намного повысить его гибкость.

HTML

В AJAX очень важна гибкость решений
Начинать можно с любой из трех обозначенных выше частей, но мы начнем с описания самой формы. Возможно, это не самый лучший вариант, но для статьи он подходит: будем двигаться от более простого к более сложному. Также мы оставим за бортом материала любой HTML-код, кроме того, который будет играть хоть какую-то роль в примере.

<form>  
Велосипед:  
<input  name="radiobutton"  type="radio"  value="bicycle">  
Машина:  
<input  name="radiobutton"  type="radio"  value="car">  
Самолет:  
<input  name="radiobutton"  type="radio"  value="airplane">  
Имя  (обязательно  для  заполнения):  
<input  type="text"  name="txtName"  title="required">  
Фамилия:  
<input  type="text"  name="txtSurname">  
  
<select  name="selectYesNo">  
<option  value="selectedYes">Да</option>  
<option  value="selectedNo">Нет</option>  
</select>  
  
<input  type="button"  value="go"  onClick="sendRequest(this.form,  'process.php')">  
</form>  
<div  id="results"  />

Рассмотрим код. Первыми у нас идут три элемента radio button для значений "Велосипед", "Машина" и "Самолет". Затем следуют два текстовых поля для ввода имени и фамилии пользователя. Обращу внимание здесь на поле с именем txtName. Его атрибут title имеет значение required; это понадобится нам во время валидации формы. Иными словами, пользователь не сможет отправить данные на сервер, пока оно не будет заполнено.

В конце же формы есть выпадающий список с двумя вариантами "Да" и "Нет" и кнопка, которая по нажатии вызывает JavaScript-функцию под названием sendRequest. Она посылает данные, полученные из формы, на сервер, но детально мы об этом поговорим чуть позже. А пока хочу обратить внимание на самую последнюю строчку кода. Это контейнер для отображения полученных с сервера результатов. Какими именно они будут, определяет PHP-скрипт, о котором пойдет речь дальше.

PHP

Поскольку наш материал ориентирован именно на разбор AJAX-функционала, связанного с обработкой форм, то серверной части мы уделим наименьшее внимание. В качестве примера используется сильно урезанный и упрощенный PHP-код, который берет данные формы, переданные JavaScript-функцией, и возвращает их уже отформатированными согласно указанному виду. Замечу, что на данной стадии мы на самом деле можем делать с ними все, что требуется.

if(isset($_GET['rnd982g']))  {  
    foreach($_GET  as  $a  =>  $b)  {  
        if($a  ==  "rnd982g")  {  
            //  пропускаем  случайное  число,  которое  используется  только  
            //  для  предотвращения  автоматического  кеширования  браузером  
        }  else  {  
        echo  "<b>$a</b>:  ".stripslashes(htmlentities($b))."";  
        }  //  if  
    }  //foreach  
die;  
}

Думаю, смысла разбирать каждую строчку кода нет смысла. Однако посмотрим на него в целом, остановившись на случайном числе, которое мы используем исключительно для предотвращения автоматического кеширования данных веб-браузером. Без включения в код этого момента велик риск сбоев во время передачи информации от клиента на сервер, и в главе материала, посвященной JavaScript-части, мы еще раз на нем остановимся. Также, как видно из примера, наше решение построено так, что PHP-часть очень легко расширяется. К примеру, мы совершенно безболезненно можем добавить в нее код для отправки электронного уведомления или для добавления полученной информации в базу данных. Сейчас же скрипт на серверной стороне просто выводит результат, который затем транслируется в упомянутом выше контейнере div.

JavaScript

JavaScript-часть в нашем решении состоит всего из 4 функций
Самое важное в рамках сегодняшнего материала — это, пожалуй, JavaScript-часть. Она состоит всего из четырех не слишком сложных функций, которые отвечают за все необходимое. Разбираться с ними мы будем по порядку. Первой идет функция, которая отвечает за создания объекта XMLHttpRequest. Здесь все в целом достаточно тривиально: в зависимости от веб-браузера пользователя скрипт выбирает соответствующий вариант работы. Больше эта функция ничего не делает.

function  createXMLHttpRequest()  {  
    var  xhr;  
    if(window.XMLHttpRequest)  {  //  если  используется  браузер,  отличный  от  Microsoft  Internet  Explorer  
        try  {  
            xhr  =  new  XMLHttpRequest();  
        }  catch(e)  {  
            xhr  =  false;  
        }  
    }  else  if(window.ActiveXObject)  {  //  если  используется  Microsoft  Internet  Explorer  
        try  {  
            xhr  =  new  ActiveXObject("Microsoft.XMLHTTP");  
        }  catch(e)  {  
            xhr  =  false;  
        }  
    }  
    return  xhr;  
}

Однако простого описания функции недостаточно. В самое начало JavaScript-кода (это будет, скорее всего, внешний подключаемый файл) еще необходимо добавить следующую строку.

var  x_request  =  createXMLHttpRequest();

Таким образом, объект XMLHttpRequest будет создаваться автоматически, как только внешний JavaScript-файл будет загружен. Идем дальше.

function  getForm(fobj)  {  
    var  str  =  "";  
    var  ft  =  "";  
    var  fv  =  "";  
    var  fn  =  "";  
    var  els  =  "";  
    for(var  i  =  0;i  <  fobj.elements.length;i++)  {  
        els  =  fobj.elements[i];  //  текущий  элемент  
        ft  =  els.title;  //  title  элемента  
        fv  =  els.value;  //  value  элемента  
        fn  =  els.name;  //  name  элемента  
        switch(els.type)  {  //  обрабатываем  данные  согласно  типу  элемента  
            case  "text":  
            case  "hidden":  
            case  "password":  
            case  "textarea":  
                //  проверяем,  обязательно  ли  это  поле  для  заполнения  или  нет  
                if(encodeURI(ft)  ==  "required"  &&  encodeURI(fv).length  <  1)  {  
                    alert('''+fn+''  is  a  required  field,  please  complete.');  
                    els.focus();  
                    return  false;  
                }  
                str  +=  fn  +  "="  +  encodeURI(fv)  +  "&";  
                break;  
  
            case  "checkbox":  
            case  "radio":  
                if(els.checked)  str  +=  fn  +  "="  +  encodeURI(fv)  +  "&";  
                break;  
  
            case  "select-one":  
                str  +=  fn  +  "="  +  
                els.options[els.selectedIndex].value  +  "&";  
                break;  
        }  //  switch  
    }  //  for  
    str  =  str.substr(0,(str.length  -  1));  
    return  str;  
}

Функция под названием getForm очень тесно связана с функцией sendRequest, которая идет следом. getForm осуществляет обработку данных. Другими словами, она вначале берет информацию из всей формы, а затем последовательно обрабатывает ее в соответствии с инструкциями внутри switch. Мы не стали писать их для каждого типа, ограничившись textarea, checkbox и select-one. К слову, именно в рамках обработки textarea мы и проверяем упомянутую выше необходимость заполнения того или иного текстового поля (имеет ли атрибут title значение required).

Затем обработанные данные возвращаются в функцию sendRequest, основная задача которой отправка информации на сервер. Она привязана в HTML-коде к кнопке.

function  sendRequest(frm,  file)  {  
    var  rnd982g  =  Math.random();  
    var  str  =  "";  
    if(str  =  getForm(frm))  {  
        x_request.open('GET',  file+'?'+str+'&rnd982g='+rnd982g);  
        x_request.onreadystatechange  =  handleResponse;  
        x_request.send(null);  
    }  
    return  false;  
}

Валидацию получаемых данных лучше выносить в отдельную функцию
Для нормальной работы функции sendRequest требуется два параметра: frm (форма, которая обрабатывается) и file (путь к файлу на серверной стороне). Когда функция вызывается, она берет объекты формы и посылает его в функцию getFrom, где, как мы уже видели, идет обработка данных, после чего они (данные) возвращаются обратно. Затем функция sendRequest использует уже открытое AJAX-соединение (функция createXMLHttpRequest и объект x_request) для того, чтобы передать обработанные данные на сервер указанному файлу (параметр file).

Последняя функция — это handleResponse. В нее передаются уже данные, полученные с сервера.

function  handleResponse()  {  
    if(x_request.readyState  ==  4)  {  
        var  response  =  x_request.responseText;  
        document.getElementById("results").innerHTML  =  response;  
    }  
}

Здесь все еще проще, чем в предыдущих функциях. Скрипт берет данные и добавляет их в контейнер results. Разумеется, в материале мы рассмотрели лишь самый базовый функционал, связанный с процессингом и парсингом форм в AJAX, — условно говоря, скелет. Не особо напрягая фантазию, можно придумать, как имеет смысл расширить каждую из частей до вполне комплексного решения.



Скоро на сайте

  • Wordpress

    Серия статей о плагинах к движку WordPrress
  • AJAX

    Проекты и продукты, ориентированные на AJAX
  • Новые сервисы Google

    Обзор новых сервисов Google
 

Copyright © 2003—2018 Все права защищены

При использовании материалов сайта ссылка на hostinfo.ru обязательна

  • хостинг от .masterhost
  • Rambler's Top100