Отправка данных формы происходит по нажатию на кнопку Submit. Часто при этом возникает задача проверить вначале данные на корректность и только в случае их правильности отсылать на сервер. В противном случае, следует вывести предупреждение об ошибке и вернуться к редактированию. Такая тактика называется «защита от дурака» и она не позволяет вводить заведомо неверные данные. Например, вы хотите от посетителя обязательно получить адрес электронной почты. Тогда во введенной строке должен содержаться символ @, который однозначно определяет, что это именно адрес, а не что иное, и не какой-нибудь адрес, а именно электронный. Также не должно быть пробелов и других недопустимых символов вроде русских букв. Только после того, как скрипт все проверит и даст добро, форму можно отправлять на сервер.
Для «ручной» отправки формы на сервер существует метод submit
. Его использование таково (пример 1).
Пример 1. Использование метода submit
document.forms["имя формы"].submit() или
document.forms.имя формы.submit()
Проверку данных лучше всего оформить в виде отдельной функции и обращаться к ней при необходимости (пример 2). В данном случае создается функция validForm, которая проверяет, чтобы введенное в текстовом поле значение было больше нуля, но меньше десяти. При вводе текста или иного числа выводится предупреждение, сами данные формы отправляются только при корректно заданном числе.
Пример 2. Проверка данных формы
<html>
<body>
<head>
<script language="JavaScript">
function validForm(f) {
d = parseInt(f.num.value); // Преобразуем в целое число
if(!d || d < 1 || d > 10) alert("Что-то неправильно введено") // Выводим предупреждение
else f.submit()
// Отправляем на сервер
}
</script>
</head>
<body>
<form action=/cgi-bin/add.cgi onSubmit="validForm(this); return false"
>
Введите число от 1 до 10<br>
<input type=text name=num>
<input type=submit value="Отправить">
</form>
</body>
</html>
В примере отправка данных происходит только после выполнения нашей собственной функции validForm. Чтобы не обращаться к форме через семейство forms, можно передать в качестве параметра ключевое слово this
. Это гораздо короче и удобней, в самой функции теперь достаточно использовать f.submit() для отправки, где f — аргумент функции, указывающий на форму. Строку «return false» при вызове события onSubmit добавить надо обязательно. Она отвечает за то, чтобы данные не отправлялись на сервер после завершения работы функции validForm.
Еще один способ отправки данных формы на сервер с предварительной их проверкой заключается в использовании события onClick. В форму добавляется обычная кнопка, на которую это событие и <навешиваем> (пример 3).
Пример 3. Использование события onClick
<html>
<body>
<head>
<script language="JavaScript">
function validForm(f) {
d = parseInt(f.num.value); // Преобразуем в целое число
if(!d || d < 1 || d > 10) alert("Что-то неправильно введено") // Выводим предупреждение
else f.submit()
// Отправляем на сервер
}
</script>
</head>
<body>
<form action=/cgi-bin/add.cgi onSubmit="return false"
>
Введите число от 1 до 10<br>
<input type=text name=num>
<input type=button value="Отправить" onClick="validForm(this.form)"
>
</form>
</body>
</html>
Событие onSubmit, которое указано в теге FORM
вроде и не нужно, но оно выполняет определенную задачу. Данные формы можно отправить на сервер и нажатием на кнопку Enter клавиатуры, когда фокус находится на элементе формы. Тогда происходит отправка на сервер, минуя наше событие onClick и соответственно проверку данных. Чтобы это не случилось, добавляем строку onSubmit="return false".
После получения введенного в текстовом поле значения, идет проверка на то, что это число и что оно меньше десяти, но больше нуля. Только в этом случае запускается метод submit. Обратите внимание, в данном случае аргументом функции validForm служит ключевое слово this.form
, а не this
, как в примере 2.
www.i2r.ru
На днях мне понадобилось реализовать отправку данных формы на сервер (submit формы), но с предварительной обработкой события формы onsubmit. Все бы ничего, если бы это можно было бы сделать при обычном нажатии на кнопку submit, но задача была немного усложнена тем, что сабмитить форму надо было автоматически, а не по запросу пользователя. В моем случае — по таймеру.
Естественно, при отправке данных на сервер, необходимо было воспользоваться JavaScript методом form.submit (). Каково же было мое удивление, когда я обнаружил, что метод отправки данных с помощью кнопки submit и работа JavaScript метода формы submit () кардинально отличаются.
Для того чтобы наглядно продемонстрировать поведение данных методов, я приведу их исходники и примеры работы.
Пример отправки данных на сервер (post) с помощью обычной кнопки <input type=»submit» /> и предварительная обработка onsubmit будет выглядеть так:
<html> <body> <form name="myform" onsubmit="alert('Отправка данных на сервер')" method="post"> <input type="text" name="data" value="Данные" /> <a href="javascript:document.myform.submit()">Отправить</a> </form> </body> </html>
при таком коде HTML, поведение формы будет следующим: если нажать кнопку «Отправить», сначала выскочит окошко с предупреждением об отправке данных на сервер, а после нажатия на кнопку «ОК», данные будут отправлены на сервер.
А что же будет, если заменить кнопку submit на JavaScript метод form.submit ()?
<html> <body> <form name="myform" onsubmit="alert('Отправка данных на сервер')" method="post"> <input type="text" name="data" value="Данные" /> <a href="javascript:document.myform.submit()">Отправить</a> </form> </body> </html>
а вот в этом случае, и произойдет то самое, странное поведение формы — событие onsubmit не сработает, но данные будут отправлены на сервер.
После длительных опытов, было определено, что браузеры не следуют спецификации HTML. События обрабатываются только действиями пользователя, но не программными действиями.
А что же по этому поводу говорит спецификация W3C и основные производители браузеров.
Спецификация W3C Document Object Model (DOM) Level 2 HTML Specification говорит, что метод submit () — «submits the form. It performs the same action as a submit button.» (сабмитит форму. Определяет то же действие, что и кнопка submit).
Производитель браузера FireFox, компания Mozilla сообщает, что onsubmit «Executes JavaScript code when a submit event occurs; that is, when a user submits a form.» (выполняет JavaScript код, когда возникает событие submit; это происходит в тот момент, когда пользователь сабмитит форму). Заметьте, что они уточняют «когда пользователь…», это в принципе исключает сабмит формы при вызове метода JavaScript.
Так же пишет и компания Netscape/Sun.
У Microsoft более лаконичное описание, «The submit method does not invoke the onsubmit event handler.» (Метод submit не вызывает событие onsubmit).
Как же выйти из этой ситуации?
Одним из решений может быть создание невидимой кнопки submit и вызов ее метода click (). Но это не сильно красивое решение. Поэтому можно подключить библиотеку jQuery и написать несколько строк кода на JavaScript для программной генерации событий.
$.fn.fireEvent = function(eventType) { return this.each(function() { if (document.createEvent) { var event = document.createEvent("HTMLEvents"); event.initEvent(eventType, true, true); return !this.dispatchEvent(event); } else { var event = document.createEventObject(); return this.fireEvent("on" + eventType, event) } }); };
Использовать данный метод очень просто. С помощью селектора jQuery находим нужный нам объект и вызываем метод fireEvent (), передав ему в качестве параметра, имя нужного события, без приставки on.
$("myform").fireEvent("submit");
На просторах сети, я находил еще одно решение — это использование метода trigger (), вместо метода fireEvent (), только он тоже не работает так как надо, потому и не буду его приводить тут.
Если вам понадобятся примеры исходных кодов, можете смело заходить на каталог исходников и поискать нужный код.
generaltea.ru
// Submit form with id function. function submit_by_id() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { document.getElementById("form_id").submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Id : " + document.getElementById("form_id").getAttribute("id") + "nn Form Submitted Successfully......"); } } // Submit form with name function. function submit_by_name() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { var x = document.getElementsByName('form_name'); x[0].submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Name : " + document.getElementById("form_id").getAttribute("name") + "nn Form Submitted Successfully......"); } } // Submit form with class function. function submit_by_class() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { var x = document.getElementsByClassName("form_class"); x[0].submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Class : " + document.getElementById("form_id").getAttribute("class") + "nn Form Submitted Successfully......"); } } // Submit form with HTML <form> tag function.
unction submit_by_tag() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { var x = document.getElementsByTagName("form"); x[0].submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Tag : <form>nn Form Submitted Successfully......"); } } // Name and Email validation Function. function validation() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; var emailReg = /^([w-.]+@([w-]+.)+[w-]{2,4})?$/; if (name === '' || email === '') { alert("Please fill all fields...!!!!!!"); return false; } else if (!(email).match(emailReg)) { alert("Invalid Email...!!!!!!"); return false; } else { return true; } }
www.formget.com
HTML page usually uses a
<form name=sp action="formtest.php" method="post"> Name: <input name="n" type="text" style="width:260px;height:22px;font-size:20px"> <input style="font-size:15px;height:26px;" type=submit value="Submit"/> </form> /*****formtest.php*****/ <?php if (isset($_POST['n']) && $_POST['n'] != "") { echo "Name is: " . $_POST['n']; } else echo "Nothing there."; ?>
There is a button, its type is
Sometimes javascript is used to check the input values before submitting to the handling file. This can be done by adding an
<script language="javascript"> function checkform() { var v=document.sf.sfn.value; for (var i = 0; i < v.length; i++) { if ((v.substring(i,i+1) >= 0 && v.substring(i, i+1) <= 9)) { alert("Error! Name contains number."); return false; } } return true; }</script> <form name=sf action="formcheck.php" method="post" onsubmit="return checkform();"> Name: <input name="n" type="text" style="width:260px;height:22px;font-size:20px"> <input style="font-size:15px;height:26px;" type=submit value="Submit"/> </form> /*****formcheck.php*****/ <?php if (isset($_POST['sfn']) && $_POST['sfn'] != "") { echo "Name is: " . $_POST['sfn']; } else echo "Nothing there."; ?>
javascript can also be used for form submit, by adding an
<script language="javascript"> function submitform() { document.forms["sp2"].submit(); }</script> <form name=sp2 action="formtest2.php" method="post"> Name: <input name="n2" type="text" style="width:260px;font-size:22px"> <input style="font-size: 17px" type=button onClick="submitform()" value="Submit"/> </form> /*****formtest2.php*****/ <?php if (isset($_POST['n2']) && $_POST['n2'] != "") { echo "Name is: " . $_POST['n2']; } else echo "Nothing there."; ?>
We can use javascript to submit the form using
<form name=sp3 action="formtest3.php" method="post"> Name: <input name="n" type="text" style="width:260px;font-size:22px"> <a href="javascript:document.forms['sp3'].submit()"> <u>Submit</u></a> <a href="javascript:document.forms['sp3'].reset()"> <u>Reset</u></a> </form> /*****formtest3.php*****/ <?php if (isset($_POST['n3']) && $_POST['n3'] != "") { echo "Name is: " . $_POST['n3']; } else echo "Nothing there."; ?>
javascript can also be used for form and input box validations, please click here for details.
www.endmemo.com
Работа с формами
Сейчас мы поговорим о различных приемах работы сценариев JavaScript с HTML-формами.
Если в HTML-документе определена форма, то она доступна сценарию JavaScript как объект, входящий в объект document
с именем, заданным атрибутом NAME
тега FORM
.
Свойства форм
Форма имеет два набора свойств, состав одного из которых фиксированный, а состав другого зависит от того, какие элементы определены в форме.
Свойства первого набора
- action. Значение атрибута
ACTION
тегаFORM
. - encoding. Значение атрибута
ENCTYPE
тегаFORM
. - method. Значение атрибута
METHOD
тегаFORM
. - target. Значение атрибута
TARGET
тегаFORM
. - elements. Массив всех элементов формы.
- length. Размер массива elements.
Большинство свойств первого набора просто отражает значение соответствующих атрибутов тега FORM
. Что же касается массива elements
, то в нем находятся объекты, соответствующие элементам, определенным в форме. Эти объекты образуют второй набор свойств формы. Адресоваться к этим объектам можно как к элементам массива elements
, причем первому элементу формы будет соответствовать элемент с индексом 0, второму — с индексом 1 и т.д. Однако удобнее обращаться к элементам формы по их именам, заданным атрибутом NAME
.
Элементы форм
Кнопки (BUTTON, RESET, SUBMIT)
Свойства
- name. Имя объекта.
- value. Надпись на кнопке.
Метод
- click( ). Вызов этого метода тождественен щелчку мышкой по кнопке.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html;charset=utf-8"> <script> <!-- function btnClick() { var Txt1 = ""; var Txt2 = ""; Txt1 = document.Test.bt.value; Txt2 = document.Test.bt.name; document.getElementById('ex1').innerHTML="<HR>"+ "Вы нажали кнопку: " + Txt1.bold() + " с именем: " + Txt2.bold() +"<HR>"; } //--> </script> </head> <body> <H1>Нажатие кнопки</H1> <div id="ex1"></div> <FORM NAME="Test"> <INPUT TYPE="button" NAME="bt" VALUE="Щелкни здесь!" onClick="btnClick();"> </FORM> </body> </html>
Флажок (CHECKBOX)
Свойства
- name. Имя объекта.
- value. Надпись на кнопке.
- checked. Состояние флажка:
true
— флажок установлен,false
— флажок не установлен. - defaultChecked. Отражает наличие атрибута
CHECKED
:true
— есть,false
— нет.
Метод
- click( ). Вызов этого метода меняет состояние флажка.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html;charset=utf-8"> </head> <body> <H1>Метод click флажка</H1> <FORM NAME="Test"> Флажок <INPUT TYPE="checkbox" NAME="ch"> <BR>Состояние флажка можно изменить и этой кнопкой <INPUT TYPE="button" VALUE="Смена состояния" onClick="document.Test.ch.click();"> </FORM> </body> </html>
Переключатель (RADIO)
Свойства
- name. Имя объекта.
- value. Надпись на кнопке.
- length. Количество переключателей в группе.
- checked. Состояние переключателя:
true
— переключатель включен,false
— выключен. - defaultChecked. Отражает наличие атрибута
CHECKED
:true
— есть,false
— нет.
Метод
- click( ). Вызов этого метода включает переключатель.
Так как группа переключателей имеет одно имя NAME
, то к переключателям надо адресоваться как к элементам массива.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <script><!-- function btnClick() { if(document.Test1.Sex[0].checked){ document.Test1.Sex[1].click(); }else{ document.Test1.Sex[0].click(); } } //--> </script> </head> <body> <H1>Метод click группы переключателей</H1> <FORM NAME="Test1"> <INPUT TYPE="RADIO" NAME="Sex" VALUE ="Man" CHECKED>Мужской <INPUT TYPE="RADIO" NAME="Sex" VALUE ="Woman">Женский <BR>Состояние переключателей можно изменить и этой кнопкой <INPUT TYPE="button" VALUE="Смена состояния" onClick="btnClick();"> </FORM> </body> </html>
Список (SELECT)
Свойства
- name. Имя объекта.
- selectedIndex. Номер выбранного элемента или первого среди выбранных (если указан атрибут
MULTIPLE
). - length. Количество элементов (строк) в списке.
- options. Массив элементов списка, заданных тегами
OPTION
.
Каждый элемент массива options является объектом со следующими свойствами:
- value. Значение атрибута
VALUE
. - text. Текст, указанный после тега
OPTION
. - index. Индекс элемента списка.
- selected. Присвоив этому свойству значение
true
, можно выбрать данный элемент. - defaultSelected. Отражает наличие атрибута
SELECTED
:true
— есть,false
— нет.
Методы
- focus( ). Передает списку фокус ввода.
- blur( ). Отбирает у списка фокус ввода.
Пример
<html> <head> <meta http-equiv=Content-Type content="text/html;charset=utf-8"> <script><!-- function btnClick2() { var sI=document.Test2.Item.selectedIndex; var Txt=""; Txt="Предложено "+document.Test2.Item.length+" напитков"+ "nВыбран "+document.Test2.Item.options[sI].text+ " (value= "+document.Test2.Item.options[sI].value+ ", index= "+document.Test2.Item.options[sI].index+")"; if(document.Test2.Item.options[sI].defaultSelected) {Txt+="nЭтот напиток выбирается по умолчанию";} alert(Txt); } //--> </script> </head> <body> <H1>Работа с готовым списком</H1> <FORM NAME="Test2"> <SELECT NAME="Item" SIZE=5> <OPTION VALUE="tea" SELECTED>Чай <OPTION VALUE ="coffee">Кофе <OPTION VALUE ="milk">Молоко <OPTION VALUE ="cocoa">Какао <OPTION VALUE ="juice">Сок </SELECT> <INPUT TYPE="button" VALUE="Пусть кофе" onClick="Test2.Item.options[1].selected=true;"> <INPUT TYPE="button" VALUE="Посмотрим" onClick="btnClick2();"> </FORM> </body> </html>
Кроме работы с готовыми списками JavaScript может заполнять список динамически. Для записи нового элемента списка используется конструктор Option c четырьмя параметрами, первый из которых задает текст, отображаемый в списке, второй — значение элемента списка, соответствующее значению атрибута VALUE
, третий соответствует свойству defaultSelected
, четвертый — свойству selected
.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html;charset=utf-8"> </head> <body> <H1>Динамическое заполнение списка</H1> <FORM NAME="Sel"> <!-- Пустой список ссылок--> <SELECT NAME="ListOfLinks"> </SELECT> <!-- Кнопка активизации выбранной ссылки--> <INPUT TYPE="button" VALUE="Переход" onClick="window.location.href=document.links[Sel.ListOfLinks.selectedIndex];"> </FORM> <A HREF="http://kdg.HtmlWeb.ru"></A> <A HREF="http://www.dstu.edu.ru/"></A> <A HREF="http://sp2all.ru/"></A> <A HREF="http://www.VseTaksi.ru/"></A> <script><!-- // Цикл по всем ссылкам for(i=0; i<document.links.length; i++) { // Создание i-элемента списка и запись в него ссылки document.Sel.ListOfLinks.options[i] = new Option(document.links[i], i, false, false); } // Выделение первого элемента в списке document.Sel.ListOfLinks.selectedIndex = 0; //--> </script> </body> </html>
Поле ввода (TEXT)
Свойства
- name. Имя объекта.
- defaultValue. Начальное содержимое поля.
- value. Текущее содержимое поля.
Методы
- focus( ). Передает полю фокус ввода.
- blur( ). Отбирает у поля фокус ввода.
- select( ). Выделяет содержимое поля.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html;charset=utf-8"> <script> <!-- function Complete() { var Elem="Фамилия: " + document.Sel1.Family.value + "nИмя: " + document.Sel1.Name.value + "nВозраст: " + document.Sel1.Age.value + "nТелефон: " + document.Sel1.Phone.value; alert(Elem); } function CheckAge(age) { if(age<18) return "18"; else return age; } //--> </script> </head> <body> <H1>Заполните анкету</H1> <FORM NAME="Sel1"> <!-- Анкета --> <TABLE> <TR><TD><B>Фамилия:<B></TD> <TD><INPUT NAME="Family" SIZE=20 onBlur="this.value=this.value.toUpperCase()"></TD></TR> <TR><TD><B>Имя:<B></TD> <TD><INPUT NAME="Name" SIZE=20 onBlur="this.value=this.value.toUpperCase()"></TD></TR> <TR><TD><B>Возраст:<B></TD> <TD><INPUT NAME="Age" SIZE=3 VALUE="18" onBlur="this.value=CheckAge(this.value)" onFocus="this.select()"></TD></TR> <TR><TD><B>Телефон:<B></TD> <TD><INPUT NAME="Phone" SIZE=10></TD></TR> </TABLE> <!-- Кнопки готовности и сброса --> <INPUT TYPE="button" VALUE="Готово" onClick="Complete();"> <INPUT TYPE="reset" VALUE="Сброс"> </FORM> </body> </html>
Обратите внимание на то, что символы фамилии и имени при потере фокуса соответствующими полями преобразуются в прописные. Для этого используется метод toUpperCase
, определенный во встроенном классе строк.
Текстовая область (TEXTAREA)
Свойства
- name. Имя объекта.
- defaultValue. Начальное содержимое области.
- value. Текущее содержимое области.
Методы
- focus( ). Передает области фокус ввода.
- blur( ). Отбирает у области фокус ввода.
- select( ). Выделяет содержимое области.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <script> <!-- var OK="Тетя Эльза чувствует себя хорошо.nЮстас."; var Problem="Тетя Эльза заболела.nЮстас."; function getDate() { var today=new Date(); return today.toLocaleString()+"n"; } function CheckRadio(form,value) { if(value=="Good") form.Letter.value=getDate()+OK; else form.Letter.value=getDate()+Problem; } //--> </script> </head> <body lang=RU> <H1>Отправьте телеграмму</H1> <FORM NAME="Sel2"> <label><INPUT TYPE="radio" NAME="Code" VALUE="Good" onClick="if(this.checked) CheckRadio(this.form,this.value);"> Явка в норме </label> <BR> <label><INPUT TYPE="radio" NAME="Code" VALUE="Bad" onClick="if(this.checked) CheckRadio(this.form,this.value);"> Явка провалена </label> <TEXTAREA NAME="Letter" ROWS=3 COLS=35> </TEXTAREA> <INPUT TYPE="button" VALUE="Готово" onClick="alert(document.Sel2.Letter.value);"> <INPUT TYPE="reset" VALUE="Сброс"> </FORM> </body> </html>
Для установки курсора в определенное место textarea-области используйте следующую кросбраузерную функцию:
<form> <textarea id="textArea">Это тестовая область</textarea> <input type="button" onclick="setCaretPosition('textArea', 5);" value="Установить курсор"> </form> <script> function setCaretPosition(o, pos) { o=document.getElementById(o); if(o.setSelectionRange) { o.focus(); o.setSelectionRange(pos,pos); }else if (o.createTextRange) { // IE var range = o.createTextRange(); range.collapse(true); range.moveEnd('character', pos); range.moveStart('character', pos); range.select(); } } </script>
Поле ввода пароля (PASSWORD)
Свойства
- name. Имя объекта.
- defaultValue. Начальное содержимое поля.
- value. Текущее содержимое поля.
Методы
- focus( ). Передает полю фокус ввода.
- blur( ). Отбирает у поля фокус ввода.
- select( ). Выделяет содержимое поля.
Пример
<html> <head> <meta http-equiv="Content-Type" content="text/html;charset=utf-8"> <script><!-- function Complete1() { if(document.Sel3.Pwd.value==document.Sel3.Pwd1.value) alert("Вас зарегистрировалиnID="+document.Sel3.Id.value+"nPassword="+document.Sel3.Pwd.value); else alert("Ошибка при вводе пароляnПопробуйте еще раз"); } //--> </script> </head> <body> <H1>Регистрация</H1> <FORM NAME="Sel3"> <TABLE> <TR><TD><B>Идентификатор:<B></TD> <TD><INPUT NAME="Id" SIZE=20 onBlur="this.value=this.value.toUpperCase()"></TD></TR> <TR><TD><B>Пароль:<B></TD> <TD><INPUT TYPE="password" NAME="Pwd" SIZE=20 onFocus="this.select();"></TD></TR> <TR><TD><B>Проверка пароля:<B></TD> <TD><INPUT TYPE="password" NAME="Pwd1" SIZE=20 onFocus="this.select();"></TD></TR> </TABLE> <INPUT TYPE="button" VALUE="Готово" onClick="Complete1();"> <INPUT TYPE="reset" VALUE="Сброс"> </FORM> </body> </html>
Как я могу использовать select box как навигационное меню?
При использовании простого JavaScript, вы можете использовать select box для передвижения по сайту. Рассмотрите этот пример:
<FORM name="navForm"> <select name="menu" onChange = "self.location = document.navForm.menu[document.navForm.menu.selectedIndex].value;"> <option value="home.html">Home</option> <option value="links.html">Links</option> <option value="contact.html">Contact Info</option> </select>
Просто сохраните URL различных страниц в option value. Обработчик события OnChange вызовет перенаправление расположения, когда значение в поле изменено.
Вы могли бы использовать этот код, чтобы изменить расположение другого фрейма изменением ‘self.location =’ на ‘top.framename.location =‘
Как я могу использовать картинку для кнопки submit?
Часто возникает вопрос: «Как инициировать форму по картинке, а не по кнопке submit?» Решение столь же просто, как этот пример:
<form> <input type="image" name="cancel" src="cancel.gif" alt="Cancel!" border=0> <input type="image" name="continue" src="continue.gif" alt="Click to Continue" border=0> </form>
Когда нажимается любая кнопка, форма инициируется и координаты x/y щелчка мыши на кнопке загружаются в объект запроса. Например, если пользователь выбрал Cancel!, объект запроса будет содержать переменные cancel.x и cancel.y. Точно так же щелчок на Continue привел бы к переменным continue.x и continue.y.
Здесь важно отметить, что элементы .x и .y — не переменные объектов continue или cancel, а фактически часть имени «continue.x». Следовательно, нельзя использовать типичный метод для определения существования одного из дочерних объектов запроса:
if (request.normalItem) act(); if (request.continue.x) // Noooo! Produces horrible error messages! doContinuingThings();
Тем не менее рассмотрите это:
if (request['normalItem']) act(); if (<B>request['continue.x']</B>) // Much better :) doContinuingThings();
Благодаря названным массивам JavaScript, можно проверить какая картинка инициировала форму.
Для некоторых приложений, полезно знать координаты курсора на нажатой картинке. Эта информация, конечно, содержится в парах image_element.x и image_element.y. Следующий серверный JavaScript мог бы использоваться для этого:
x=0; y=0; if ((request['my_submit_image.x']) (request['my_submit_image.y'])) { x = parseInt(request['my_submit_image.x']); y = parseInt(request['my_submit_image.y']); }
Передача данных между формами на различных страницах
В качестве простого примера, предположите, что ваша «домашняя» страница запрашивает имя пользователя, затем использует это имя, чтобы обратиться к пользователю на следующих страницах. Вы можете взять имя, используя форму, затем использовать JavaScript для передачи имени пользователя в следующую страницу, используя URL. Последующая страница могла бы затем анализировать имя пользователя из URL, используя информацию в document.search.
home.html
<html> <head> <script language="JavaScript"> function nextPage() { self.location = "next.html?name=" + escape(document.theForm.userName.value); // Use escape() any time there might be spaces or } // non-alpa characters </script> </head> <body> <form onSubmit = "nextPage();return false;"> Enter your name: <input type=text name=userName> <input type=submit> </form> </body> </html>
next.html
userName = document.search; userName = userName.substring(userName.indexOf("=")+1); document.write("Greetings, " + userName + "<P>");
Почему document.formName.selectObject.value не отражает значение выбранного пункта в списке?
Потому что объект работает не таким образом. Правильный и полный синтаксис для доступа к VALUE только что выбранным полем в списке — это:
Document.form.selectObject[document.form.selectObject.selectedIndex].value
Для доступак тексту элемента используйте свойство text:
Document.form.selectObject[document.form.selectObject.selectedIndex].text
Как мне получить значение выбранной в данный момент radio button в radio group или группе checkboxes?
Существует свойство, созданное в объекте form для каждой radio buttons или checkboxes с тем же самым именем. Например, следующий HTML код:
<form name='theForm'> <input type=radio name="gender" value="Male">Male <input type=radio name="gender" value="Female">Female <input type=radio name="gender" value="Evasive">Not Specified </form>
приводит к созданию 3-х элементов массива, вызываемых с помощью document.theForm.gender. Чтобы определить значение выбранной кнопки (или checkbox’а), вам нужно проверить свойство checked каждого из элементов. Например:
function checkIt() { theGroup = document.theForm.gender; for (i=0; i< theGroup.length; i++) { if (theGroup[i].checked) { alert("The value is " + theGroup[i].value); break; } } }
Для получения и установки значения radio button value на javascript можно использовать следующие функции:
function getCheckedValue(radioObj) { if(!radioObj) return ""; var radioLength = radioObj.length; if(radioLength == undefined) if(radioObj.checked) return radioObj.value; else return ""; for(var i = 0; i < radioLength; i++) { if(radioObj[i].checked) { return radioObj[i].value; } } return ""; } function setCheckedValue(radioObj, newValue) { if(!radioObj) return; var radioLength = radioObj.length; if(radioLength == undefined) { radioObj.checked = (radioObj.value == newValue.toString()); return; } for(var i = 0; i < radioLength; i++) { radioObj[i].checked = false; if(radioObj[i].value == newValue.toString()) { radioObj[i].checked = true; } } }
Как мне получить форму, чтобы инициировать процесс запуска клавишей Enter?
Форма отправляется, если нажата клавиша enter, в то время как единственный входной текстовый элемент формы имеет фокус. Вы можете вызывать подобное поведение в форме, имеющей более одного элемента, разбивая форму на ряд отдельных форм, так, чтобы каждая форма имела только один текстовый элемент. Используйте обработчик события onSubmit (или action=»javascript:myFunction();«) для накопления данных из других форм в вашей странице и инициируйте их все сразу.
Как я могу отключить поле текстового ввода?
Используйте обработчик onfocus для вызова функции blur():
<INPUT TYPE="text" NAME="aTextField" ONFOCUS="this.blur()">
Если вы хотите динамически отключать/включать поле, используйте функцию skip (e)
{ this.blur(); } <A HREF="javascript:document.formName.aTextField.onfocus = skip; void 0">disable text field</A> <A HREF="javascript:document.formName.aTextField.onfocus = null; void 0">enable text field</A>
Как сделать загрузку страницы при выборе флажка?
Используйте обработчик OnChange для вызова функции submit():
<form method=get OnChange='this.submit();'> <input type=checkbox name="fnew">Только новые </form>
Сохранение данных в локальное хранилище браузера:
sessionStorage — запоминает результат пока открыт сайт во вкладке(окне), можно свободно перемещаться по сайту, обновлять страницы, но не закрывать окно браузера(вкладку).
localStorage — запоминает результат на очень долгое время, пока пользователь не очистит локальное хранилище браузера. Можно через несколько дней зайти на сайт и увидеть ранее заполненную форму.
<style> #idVhod { display: none; /* изначально скрыт */ } </style> <button onclick="onclickVhod()">открыть</button> <span id="idVhod">скрытый текст</span> <script> var idVhod = document.getElementById('idVhod'); function onclickVhod() { idVhod.style.display = (idVhod.style.display == 'inline') ? '' : 'inline' localStorage.setItem('hide', idVhod.style.display); // сохраняем значение в объект hide } if(localStorage.getItem('hide') == 'inline') { // если значение объекта hide "inline" document.getElementById('idVhod').style.display = 'inline'; } //localStorage.removeItem('hide') // удалить один элемент //localStorage.clear() // удалить все элементы </script>
Особенности onClick, onSubmit, onReset
- метод click() у гиперссылки — влечет за собой вызов обработчика onClick этой ссылки
- метод click() у ЛЮБОЙ кнопки формы — влечет за собой вызов обработчика onClick этой кнопки
- метод reset() у формы — влечет за собой вызов обработчика onReset у формы
- НО метод submit() у формы — НЕ влечет за собой вызов обработчика onSubmit у формы!
DOM объект элемента INPUT:
interface HTMLInputElement : HTMLElement { attribute DOMString accept; attribute DOMString alt; attribute DOMString autocomplete; attribute boolean autofocus; attribute boolean defaultChecked; attribute boolean checked; attribute DOMString dirName; attribute boolean disabled; readonly attribute HTMLFormElement? form; readonly attribute FileList? files; attribute DOMString formAction; attribute DOMString formEnctype; attribute DOMString formMethod; attribute boolean formNoValidate; attribute DOMString formTarget; attribute unsigned long height; attribute boolean indeterminate; readonly attribute HTMLElement? list; attribute DOMString max; attribute long maxLength; attribute DOMString min; attribute boolean multiple; attribute DOMString name; attribute DOMString pattern; attribute DOMString placeholder; attribute boolean readOnly; attribute boolean required; attribute unsigned long size; attribute DOMString src; attribute DOMString step; attribute DOMString type; attribute DOMString defaultValue; attribute DOMString value; attribute Date? valueAsDate; attribute double valueAsNumber; attribute unsigned long width; void stepUp(optional long n); void stepDown(optional long n); readonly attribute boolean willValidate; readonly attribute ValidityState validity; readonly attribute DOMString validationMessage; boolean checkValidity(); void setCustomValidity(DOMString error); readonly attribute NodeList labels; void select(); attribute unsigned long selectionStart; attribute unsigned long selectionEnd; attribute DOMString selectionDirection; void setSelectionRange(unsigned long start, unsigned long end, optional DOMString direction); };
htmlweb.ru
Creating and styling the outline of your form
Now in the body section you put two <div>
s inside of one another, one with the class="container"
attribute and the one inside it with the class="main"
attribute. These are purely for styling purposes. The code will look like this:
<div class="container"> <div class="main"> </div> </div>
While the styling for these elements can be found in the submit_javascript.css
file, looking like this:
div.container{ width: 900px; height: 610px; margin:35px auto; font-family: 'Raleway', sans-serif; } div.main{ width: 300px; padding: 10px 50px 10px; border: 2px solid gray; border-radius: 10px; font-family: raleway; float:left; margin-top:60px; }
Labels and Inputs
Now inside of the <div class="main">
we put this code:
<form action="#" method="post" name="form_name" id="form_id" class="form_class" ></form>
And inside this tag we put the code for the labels and inputs, which should look like this:
<h2>Javascript Form Submit Example</h2> <label>Name :</label> <input type="text" name="name" id="name" placeholder="Name" /> <label>Email :</label> <input type="text" name="email" id="email" placeholder="Valid Email" />
The inputs should both have the type="text"
attribute, while having names and id respectively "name"
and "email"
. Also we can put the attribute placeholder
, though it’s not obligatory.
Buttons
Now it’s time to create the submit buttons, which will be four, as we want to make make the submission once by id
, once by class
, once by name
and once by tag
.Here’s the code:
<input type="button" name="submit_id" id="btn_id" value="Submit by Id" onclick="submit_by_id()"/> <input type="button" name="submit_name" id="btn_name" value="Submit by Name" onclick="submit_by_name()"/> <input type="button" name="submit_class" id="btn_class" value="Submit by Class" onclick="submit_by_class()"/> <input type="button" name="submit_tag" id="btn_tag" value="Submit by Tag" onclick="submit_by_tag()"/>
You all know the attributes given to the button, except for maybe the onclick
attribute. That is the name of the JavaScript function, which tells the button what to do when clicked. With that we finish our job in the index.html
file, so we can deal with those functions right now.
JavaScript functions
Every button triggers a different way of behaving for the buttons they’re attributed to, namely the submit the form by class
, id
, name
, or tag
. Also we will put out an alert which will tell us if the e-mail is valid or not. For that we’re going to have a validation function, which will look like this:
// Name and Email validation Function. function validation() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; var emailReg = /^([w-.]+@([w-]+.)+[w-]{2,4})?$/; if (name === '' || email === '') { alert("Please fill all fields...!!!!!!"); return false; } else if (!(email).match(emailReg)) { alert("Invalid Email...!!!!!!"); return false; } else { return true; } }
This function gets the name and e-mail and if those are null strings puts out “Please fill all fields……!!!!!!” or if the e-mail does not match the regular email, puts out “Invalid email…..!!!!!!”.
Let’s see first the function submit_by_tag()
. The code for it will go like this:
function submit_by_tag() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { var x = document.getElementsByTagName("form"); x[0].submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Tag : <form>nn Form Submitted Successfully......"); } }
After getting the name and email values and passing them through validation, the function gets the element by tag name and submits them using the submit()
function. After that, it puts out an alert saying the name and email entered, the form tag, and a message saying that the form was submitted successfully.
Similar is what we’re going to do with the other three functions, except in them we’re going to get the elements by class, id, or name.
The code below is the submit_by_class()
function:
function submit_by_class() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { var x = document.getElementsByClassName("form_class"); x[0].submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Class : " + document.getElementById("form_id").getAttribute("class") + "nn Form Submitted Successfully......"); } }
This is the code for submit_by_name()
function:
function submit_by_name() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { var x = document.getElementsByName('form_name'); x[0].submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Name : " + document.getElementById("form_id").getAttribute("name") + "nn Form Submitted Successfully......"); } }
And finally, this is the submit_by_id()
function:
function submit_by_id() { var name = document.getElementById("name").value; var email = document.getElementById("email").value; if (validation()) // Calling validation function { document.getElementById("form_id").submit(); //form submission alert(" Name : " + name + " n Email : " + email + " n Form Id : " + document.getElementById("form_id").getAttribute("id") + "nn Form Submitted Successfully......"); } }
Styling the form
And last but not least is styling the form. We have already styled the outer <div>
s with the class="container"
and class="main"
attributes. Now we’re going to make everything else look as pretty.
First we put this code in the submit_javascript.css
file to style the title of the form and the content separator:
h2{ background-color: #FEFFED; padding: 30px 35px; margin: -10px -50px; text-align:center; border-radius: 10px 10px 0 0; } hr{ margin: 10px -50px; border: 0; border-top: 1px solid #ccc; margin-bottom: 40px; }
Now we style the inputs and labels with this CSS bit of code:
input[type=text]{ width: 100%; height: 40px; padding: 5px; margin-bottom: 25px; margin-top: 5px; border: 2px solid #ccc; color: #4f4f4f; font-size: 16px; border-radius: 5px; } label{ color: #464646; text-shadow: 0 1px 0 #fff; font-size: 14px; font-weight: bold; }
Now let’s get to the buttons.We will style them differently when in standby and when hovered. The following bit of code is their normal standby state:
#btn_id,#btn_name,#btn_class,#btn_tag{ font-size: 16px; background: linear-gradient(#ffbc00 5%, #ffdd7f 100%); border: 1px solid #e5a900; color: #4E4D4B; font-weight: bold; cursor: pointer; width: 47.5%; border-radius: 5px; margin-bottom:10px; padding: 7px 0; }
Meanwhile the code for the buttons when hovered is this:
#btn_id:hover,#btn_name:hover,#btn_class:hover,#btn_tag:hover{ background: linear-gradient(#ffdd7f 5%, #ffbc00 100%); }
And with this we’re set. The form will look like this:
Download the source code
This was an example of form submission using JavaScript.
www.webcodegeeks.com
The Submit Method
The syntax for the submit () method is:
document.forms[“nameofform”].submit();
The method must be called from within a function in your html program. You also need to assign an id to the form before the browser can recognize it. You can do this by assigning an ID attribute from within the form tab:
<form id='nameofform' action='formmail.pl'>
The submit() method can be called when a user clicks on a hyperlink, which is the most common, or an image. Let’s take a look at the code for both these scenarios:
Submitting a Form by Clicking on the Hyperlink
You can use the following code to submit a form when a hyperlink is clicked:
<script type="text/javascript"> function submitform() { document.forms["nameofform"].submit(); } </script> <form id="nameofform" action="submit-form.php"> Search: <input type='text' name='query'> <a href="javascript: submitform()">Submit</a> </form>
The above code will bring up a form with a single field called “Query” and a blank text box next to it. There will also be a submit hyperlink button which you can click to submit the data you enter in the blank text box.
Instead of a Hyperlink, you can use a clickable submit button (this is what most users are used to). To make a clickable submit button, remove the code that inserts the hyperlink “Submit” and replace it with the submit button:
<input type="submit" name="submitbutton" value="Submit" />
Here, the name is the identification tag that will be assigned to the submit button. The value field is the name that you want to appear on your button. You can make your “submit” button a go button by changing the value to “go”.
If you want the submit button to accept the data from your form, you can use the following line of code:
<form name="nameofform" action="html_form_action.asp" method="get"> First Name: <input type="text" name="user"> <input type="submit" value="Submit"> </form>
This will allow the browser to fetch the data you have entered in the “first name” field in your form.
Submitting a Form by Clicking on the Form Submit Button
You can also use an image to accept the submission of data. You need to have an image you can use with you first. You will need to define the attributes of the image (height and width) before you can use it as the submit button.
The code to make an image the submit button is as follows:
<form name="nameofform" action="submit-form.ph"> Query: <input type='text' name='query'/> <input type="image" src="image.gif"/> </form>
Here, the “image.gif” will be the name of the image that will be present on the system. You can modify the attributes of the images with the following line of code:
<img src="image.gif" width="30" height="20" border="0" />
You may need to play around with the attributes a little before the image looks small enough to be a submit button.
blog.udemy.com
Содержание
- Введение
- Величины, типы и операторы
- Структура программ
- Функции
- Структуры данных: объекты и массивы
- Функции высшего порядка
- Тайная жизнь объектов
- Проект: электронная жизнь
- Поиск и обработка ошибок
- Регулярные выражения
- Модули
- Проект: язык программирования
- JavaScript и браузер
- Document Object Model
- Обработка событий
- Проект: игра-платформер
- Рисование на холсте
- HTTP
- Формы и поля форм
- Проект: Paint
- Node.js
- Проект: веб-сайт по обмену опытом
- Песочница для кода
Я нынче ж на ученом кутеже
Твое доверье службой завоюю,
Ты ж мне черкни расписку долговую,
Чтоб мне не сомневаться в платеже.
Мефистофель, в «Фаусте» Гёте
Формы были кратко представлены в предыдущей главе в качестве способа передачи информации, введённой пользователем, через HTTP. Они были разработаны в вебе до появления JavaScript, с тем расчётом, что взаимодействие с сервером происходит при переходе на другую страницу.
Но их элементы являются частями DOM, как и остальные части страницы, а элементы DOM, представляющие поля формы, поддерживают несколько свойств и событий, которых нет у других элементов. Это делает возможным просматривать и управлять полями ввода из программ JavaScript и добавлять функциональности к классическим формам или использовать формы и поля как основу для построения приложения.
Поля
Веб-форма состоит из любого числа полей ввода, окружённых тегом
. HTML предлагает много разных полей, от простых галочек со значениями вкл/выкл до выпадающих списков и полей для ввода текста. В этой книге не будут подробно обсуждаться все виды полей, но мы сделаем небольшой их обзор.
Много типов полей ввода используют тег . Его атрибут type используется для выбора стиля поля. Вот несколько распространённых типов:
text текстовое поле на одну строку
password то же, что текст, но прячет ввод
checkbox переключатель вкл/выкл
radio часть поля с возможностью выбора из нескольких вариантов
file позволяет пользователю выбрать файл на его компьютере
Поля форм не обязательно должны появляться внутри тега . Их можно разместить в любом месте страницы. Информацию из таких полей нельзя передавать на сервер (это возможно только для всей формы целиком), но когда мы делаем поля, которые обрабатывает JavaScript, нам обычно и не нужно передавать информацию из полей через submit.
<p><input type="text" value="abc"> (text)</p> <p><input type="password" value="abc"> (password)</p> <p><input type="checkbox" checked> (checkbox)</p> <p><input type="radio" value="A" name="choice"> <input type="radio" value="B" name="choice" checked> <input type="radio" value="C" name="choice"> (radio)</p> <p><input type="file" checked> (file)</p>
Интерфейс JavaScript для таких элементов разнится в зависимости от типа. Мы рассмотрим каждый из них чуть позже.
У текстовых полей на несколько строк есть свой тег . У тега должен быть закрывающий тег
, и он использует текст внутри этих тегов вместо использования атрибута value.
<textarea> один два три </textarea>
А тег
используется для создания поля, которое позволяет пользователю выбрать один из заданных вариантов.
<select> <option>Блины</option> <option>Запеканка</option> <option>Мороженка </option> </select>
Когда значение поля изменяется, запускается событие “change”.
Фокус
В отличие от большинства элементов документа HTML, поля форм могут получать фокус ввода клавиатуры. При щелчке или выборе их другим способом они становятся активными, т.е. главными приёмниками клавиатурного ввода.
Если в документе есть текстовое поле, то набираемый текст появится в нём, только если поле имеет фокус ввода. Другие поля по-разному реагируют на клавиатуру. К примеру,
пытается перейти на вариант, содержащий текст, который вводит пользователь, а также отвечает на нажатия стрелок, передвигая выбор варианта вверх и вниз.
Управлять фокусом из JavaScript можно методами focus и blur. Первый перемещает фокус на элемент DOM, из которого он вызван, а второй убирает фокус. Значение document.activeElement соответствует текущему элементу, получившему фокус.
<input type="text"> <script> document.querySelector("input").focus(); console.log(document.activeElement.tagName); // → INPUT document.querySelector("input").blur(); console.log(document.activeElement.tagName); // → BODY </script>
На некоторых страницах нужно, чтобы пользователь сразу начинал работу с какого-то из полей формы. При помощи JavaScript можно передать этому полю фокус при загрузке документа, но в HTML также есть атрибут autofocus, который приводит к тому же результату, но сообщает браузеру о наших намерениях. В этом случае браузер может отменить это поведение в подходящих случаях, например когда пользователь перевёл фокус куда-то ещё.
<input type="text" autofocus>
Браузеры по традиции позволяют пользователю перемещать фокус клавишей Tab. Мы можем влиять на порядок перемещения через атрибут tabindex. В примере документ будет переносить фокус с текстового поля на кнопку OK, вместо того, чтобы сначала пройти через ссылку help.
<input type="text" tabindex=1> <a href=".">(help)</a> <button onclick="console.log('ok')" tabindex=2>OK</button>
По умолчанию, большинство типов элементов HTML не получают фокус. Но добавив tabindex к элементу, вы сделаете возможным получение им фокуса.
Отключённые поля
Все поля можно отключить атрибутом disabled, который существует и в виде свойства элемента объекта DOM.
<button>У меня всё хорошо</button> <button disabled>Я в отключке</button>
Отключённые поля не принимают фокус и не изменяются, и в отличие от активных, обычно выглядят серыми и выцветшими.
Когда программа находится в процессе обработки нажатия на кнопку или другой элемент, которое может потребовать общение с сервером и занять длительное время, неплохо отключать элемент до завершения действия. В этом случае, когда пользователь потеряет терпение и нажмёт на элемент ещё раз, действие не будет повторено лишний раз.
Форма в целом
Когда поле, содержится в элементе
, у его элемента DOM будет свойство form, которое будет ссылаться на форму. Элемент , в свою очередь, имеет свойство elements, содержащее массивоподобную коллекцию полей.
Атрибут name поля задаёт, как будет определено значение этого поля при передаче на сервер. Его также можно использовать как имя свойства при доступе к свойству формы elements, который работает и как объект, похожий на массив (с доступом по номерам), так и map (с доступом по имени).
<form action="example/submit.html"> Имя: <input type="text" name="name"><br> Пароль: <input type="password" name="password"><br> <button type="submit">Войти</button> </form> <script> var form = document.querySelector("form"); console.log(form.elements[1].type); // → password console.log(form.elements.password.type); // → password console.log(form.elements.name.form == form); // → true </script>
Кнопка с атрибутом type равным submit при нажатии отправляет форму. Нажатие клавиши Enter внутри поля формы имеет тот же эффект.
Отправка формы обычно означает, что браузер переходит на страницу, обозначенную в атрибуте формы action, используя либо GET либо POST запрос. Но перед этим запускается свойство “submit”. Его можно обработать в JavaScript, и обработчик может предотвратить поведение по умолчанию, вызвав на объекте event preventDefault.
<form action="example/submit.html"> Значение: <input type="text" name="value"> <button type="submit">Сохранить </button> </form> <script> var form = document.querySelector("form"); form.addEventListener("submit", function(event) { console.log("Saving value", form.elements.value.value); event.preventDefault(); }); </script>
Перехват событий “submit” полезен в нескольких случаях. Мы можем написать код, проверяющий допустимость введённых значений и сразу же показать ошибку вместо передачи данных формы. Или мы можем отключить отправку формы по умолчанию и дать программе возможность самой обработать ввод, например используя XMLHttpRequest для отправки данных на сервер без перезагрузки страницы.
Текстовые поля
Поля с тегами
и типами text и password, а также теги , имеют общий интерфейс. У их элементов DOM есть свойство value, в котором содержится их текущее содержимое в виде строки текста. Присваивание этому свойству значения меняет содержимое поля.
Свойства текстовых полей selectionStart и selectionEnd содержат данные о положении курсора и выделения текста. Когда ничего не выделено, их значение одинаковое, и равно положению курсора. Например, 0 обозначает начало текста, 10 обозначает, что курсор находится на 10-м символе. Когда выделена часть поля, свойства имеют разные значения, а именно начало и конец выделенного текста. В эти поля также можно записывать значение.
К примеру, представьте, что вы пишете статью про Khasekhemwy, но затрудняетесь писать его имя правильно. Следующий код назначает тегу обработчик событий, который при нажатии F2 вставляет строку “ Khasekhemwy”.
<textarea></textarea> <script> var textarea = document.querySelector("textarea"); textarea.addEventListener("keydown", function(event) { // The key code for F2 happens to be 113 if (event.keyCode == 113) { replaceSelection(textarea, "Khasekhemwy"); event.preventDefault(); } }); function replaceSelection(field, word) { var from = field.selectionStart, to = field.selectionEnd; field.value = field.value.slice(0, from) + word + field.value.slice(to); // Put the cursor after the word field.selectionStart = field.selectionEnd = from + word.length; }; </script>
Функция replaceSelection заменяет текущий выделенный текст заданным словом, и перемещает курсор на позицию после этого слова, чтобы можно было продолжать печатать.
Событие “change” для текстового поля не срабатывает каждый раз при вводе одного символа. Оно срабатывает после потери полем фокуса, когда его значение было изменено. Чтобы мгновенно реагировать на изменение текстового поля нужно зарегистрировать событие “input”, которое срабатывает каждый раз при вводе символа, удалении текста или других манипуляциях с содержимым поля.
В следующем примере мы видим текстовое поле и счётчик, показывающий текущую длину введённого текста.
<input type="text"> length: <span id="length">0</span> <script> var text = document.querySelector("input"); var output = document.querySelector("#length"); text.addEventListener("input", function() { output.textContent = text.value.length; }); </script>
Галочки и радиокнопки
Поле галочки – простой бинарный переключатель. Его значение можно извлечь или поменять через свойство checked, содержащее булевскую величину.
<input type="checkbox" id="purple"> <label for="purple">Сделать страницу фиолетовой</label> <script> var checkbox = document.querySelector("#purple"); checkbox.addEventListener("change", function() { document.body.style.background = checkbox.checked ? "mediumpurple" : ""; }); </script>
Тег
используется для связи куска текста с полем ввода. Атрибут for должен совпадать с id поля. Щелчок по метке label включает поле ввода, оно получает фокус и меняет значение – если это галочка или радиокнопка.
Радиокнопка схожа с галочкой, но она связана с другими радиокнопками с тем же именем, так что только одна из них может быть выбрана.
Цвет: <input type="radio" name="color" value="mediumpurple"> Фиолетовый <input type="radio" name="color" value="lightgreen"> Зелёныйы <input type="radio" name="color" value="lightblue"> Голубой <script> var buttons = document.getElementsByName("color"); function setColor(event) { document.body.style.background = event.target.value; } for (var i = 0; i < buttons.length; i++) buttons[i].addEventListener("change", setColor); </script>
Метод document.getElementsByName выдаёт все элементы с заданным атрибутом name. Пример перебирает их (посредством обычного цикла for, а не forEach, потому что возвращаемая коллекция – не настоящий массив) и регистрирует обработчик событий для каждого элемента. Помните, что у объектов событий есть свойство target, относящееся к элементу, который запустил событие. Это полезно для создания обработчиков событий – наш обработчик может быть вызван разными элементами, и у него должен быть способ получить доступ к текущему элементу, который его вызвал.
Поля select
Поля select похожи на радиокнопки – они также позволяют выбрать из нескольких вариантов. Но если радиокнопки позволяют нам контролировать раскладку вариантов, то вид поля
определяет браузер.
У полей select есть вариант, больше похожий на список галочек, чем на радиокнопки. При наличии атрибута multiple тег позволит выбирать любое количество вариантов, а не один.
<select multiple> <option>Блины</option> <option>Запеканка</option> <option>Мороженка </option> </select>
В большинстве браузеров внешний вид поля будет отличаться от поля с единственным вариантом выбора, который обычно выглядит как выпадающее меню.
Атрибут size тега используется для задания количества вариантов, которые видны одновременно – так вы можете влиять на внешний вид выпадушки. К примеру, назначив size 3, вы увидите три строки одновременно, безотносительно того, присутствует ли опция multiple.
У каждого тега есть значение. Его можно определить атрибутом value, но если он не задан, то значение тега определяет текст, находящийся внутри тега ... Свойство value элемента отражает текущий выбранный вариант. Для поля с возможностью выбора нескольких вариантов это свойство не особо нужно, т.к. в нём будет содержаться только один из нескольких выбранных вариантов.
К тегу
поля можно получить доступ как к массивоподобному объекту через свойство options. У каждого варианта есть свойство selected, показывающее, выбран ли сейчас этот вариант. Свойство также можно менять, чтобы вариант становился выбранным или не выбранным.
Следующий пример извлекает выбранные значения из поля select и использует их для создания двоичного числа из битов. Нажмите Ctrl (или Command на Маке), чтобы выбрать несколько значений сразу.
<select multiple> <option value="1">0001</option> <option value="2">0010</option> <option value="4">0100</option> <option value="8">1000</option> </select> = <span id="output">0</span> <script> var select = document.querySelector("select"); var output = document.querySelector("#output"); select.addEventListener("change", function() { var number = 0; for (var i = 0; i < select.options.length; i++) { var option = select.options[i]; if (option.selected) number += Number(option.value); } output.textContent = number; }); </script>
Файловое поле
Файловое поле изначально было предназначено для закачивания файлов с компьютера через форму. В современных браузерах они также позволяют читать файлы из JavaScript. Поле работает как охранник для файлов. Скрипт не может просто взять и открыть файл с компьютера пользователя, но если тот выбрал файл в этом поле, браузер разрешает скрипту начать чтение файла.
Файловое поле обычно выглядит как кнопка с надписью вроде «Выберите файл», с информацией про выбранный файл рядом с ней.
<input type="file"> <script> var input = document.querySelector("input"); input.addEventListener("change", function() { if (input.files.length > 0) { var file = input.files[0]; console.log("You chose", file.name); if (file.type) console.log("It has type", file.type); } }); </script>
Свойство files элемента – массивоподобный объект (не настоящий массив), содержащий список выбранных файлов. Изначально он пуст. У элемента нет простого свойства file, потому что пользователь может выбрать несколько файлов за раз при включённом атрибуте multiple.
У объектов в свойстве files есть свойства имя (имя файла), размер (размер файла в байтах), и тип (тип файла в смысле media type - text/plain или image/jpeg).
Чего у него нет, так это свойства, содержащего содержимое файла. Чтобы получить содержимое, приходиться постараться. Так как чтение файла с диска занимает длительное время, интерфейс должен быть асинхронным, чтобы документ не замирал. Конструктор FileReader можно представлять себе, как конструктор XMLHttpRequest, только для файлов.
<input type="file" multiple> <script> var input = document.querySelector("input"); input.addEventListener("change", function() { Array.prototype.forEach.call(input.files, function(file) { var reader = new FileReader(); reader.addEventListener("load", function() { console.log("File", file.name, "starts with", reader.result.slice(0, 20)); }); reader.readAsText(file); }); }); </script>
Чтение файла происходит при помощи создания объекта FileReader, регистрации события “load” для него, и вызова его метода readAsText с передачей тому файла. По окончанию загрузки в свойстве result сохраняется содержимое файла.
Пример использует Array.prototype.forEach для прохода по массиву, так как в обычном цикле было бы неудобно получать нужные объекты file и reader от обработчика событий. Переменные были бы общими для всех итераций цикла.
У FileReaders также есть событие “error”, когда чтение файла не получается. Объект error будет сохранён в свойстве error. Если вы не хотите забивать голову ещё одной неудобной асинхронной схемой, вы можете обернуть её в обещание (см. главу 17):
function readFile(file) { return new Promise(function(succeed, fail) { var reader = new FileReader(); reader.addEventListener("load", function() { succeed(reader.result); }); reader.addEventListener("error", function() { fail(reader.error); }); reader.readAsText(file); }); }
Возможно читать только часть файла, вызывая slice и передавая результат (т.н. объект blob) объекту reader.
Хранение данных на стороне клиента
Простые HTML-странички с добавкой JavaScript могут выступать отличной основой для мини-приложений – небольших вспомогательных программ, автоматизирующих ежедневные дела. Присоединив к полям формы обработчики событий вы можете делать всё – от конвертации фаренгейтов в цельсии до генерации паролей из основного пароля и имени веб-сайта.
Когда такому приложению нужно сохранять информацию между сессиями, переменные JavaScript использовать не получится – их значения выбрасываются каждый раз при закрытии страницы. Можно было бы настроить сервер, подсоединить его к интернету и тогда приложение хранило бы ваши данные там. Это мы разберём в главе 20. Но это добавляет вам работы и сложности. Иногда достаточно хранить данные в своём браузере. Но как?
Можно хранить строковые данные так, что они переживут перезагрузку страниц - для этого надо положить их в объект localStorage. Он разрешает хранить строковые данные под именами (которые тоже являются строками), как в этом примере:
localStorage.setItem("username", "marijn"); console.log(localStorage.getItem("username")); // → marijn localStorage.removeItem("username");
Переменная в localStorage хранится, пока её не перезапишут, удаляется при помощи removeItem или очисткой локального хранилища пользователем.
У сайтов с разных доменов – разные отделения в этом хранилище. То есть, данные, сохранённые с вебсайта в localStorage, могут быть прочтены или перезаписаны только скриптами с этого же сайта.
Также браузеры ограничивают объём хранимых данных, обычно в несколько мегабайт. Это ограничение, вкупе с тем фактом, что забивание жёстких дисков у людей не приносит прибыли, предотвращает отъедание места на диске.
Следующий код реализует простую программу для ведения заметок. Она хранит заметки в виде объекта, ассоциируя заголовки с содержимым. Он кодируется в JSON и хранится в localStorage. Пользователь может выбрать записку через поле
и поменять её текст в . Добавляется запись по нажатию на кнопку.
Заметки: <select id="list"></select> <button onclick="addNote()">новая</button><br> <textarea id="currentnote" style="width: 100%; height: 10em"> </textarea> <script> var list = document.querySelector("#list"); function addToList(name) { var option = document.createElement("option"); option.textContent = name; list.appendChild(option); } // Берём список из локального хранилища var notes = JSON.parse(localStorage.getItem("notes")) || {"что купить": ""}; for (var name in notes) if (notes.hasOwnProperty(name)) addToList(name); function saveToStorage() { localStorage.setItem("notes", JSON.stringify(notes)); } var current = document.querySelector("#currentnote"); current.value = notes[list.value]; list.addEventListener("change", function() { current.value = notes[list.value]; }); current.addEventListener("change", function() { notes[list.value] = current.value; saveToStorage(); }); function addNote() { var name = prompt("Имя записи", ""); if (!name) return; if (!notes.hasOwnProperty(name)) { notes[name] = ""; addToList(name); saveToStorage(); } list.value = name; current.value = notes[name]; } </script>
Скрипт инициализирует переменную notes значением из localStorage, а если его там нет – простым объектом с одной записью «что купить». Попытка прочесть отсутствующее поле из localStorage вернёт null. Передав null в JSON.parse, мы получим null обратно. Поэтому для значения по умолчанию можно использовать оператор || .
Когда данные в note меняются (добавляется новая запись или меняется текущая), для обновления хранимого поля вызывается функция saveToStorage. Если б мы рассчитывали, что у нас будут храниться тысячи записей, это было бы слишком накладно, и нам пришлось бы придумать более сложную процедуру для хранения – например, своё поле для каждой записи.
Когда пользователь добавляет запись, код должен обновить текстовое поле, хотя у поля и есть обработчик “change”. Это нужно потому, что событие “change” происходит, только когда пользователь меняет значение поля, а не когда это делает скрипт.
Есть ещё один похожий на localStorage объект под названием sessionStorage. Разница между ними в том, что содержимое sessionStorage забывается по окончанию сессии, что для большинства браузеров означает момент закрытия.
Итог
HTML предоставляет множество различных типов полей формы – текстовые, галочки, множественного выбора, выбора файла.
Из JavaScript можно получать значение и манипулировать этими полями. По изменению они запускают событие “change”, по вводу с клавиатуры – “input”, и ещё много разных клавиатурных событий. Они помогают нам отловить момент, когда пользователь взаимодействует с полем ввода. Свойства вроде value (для текстовых полей и select) или checked (для галочек и радиокнопок) используются для чтения и записи содержимого полей.
При передаче формы происходит событие “submit”. Обработчик JavaScript затем может вызвать preventDefault этого события, чтобы остановить передачу данных. Элементы формы не обязаны быть заключены в теги
.
Когда пользователь выбрал файл с жёсткого диска через поле выбора файла, интерфейс FileReader позволит нам добраться до содержимого файла из программы JavaScript.
Объекты localStorage и sessionStorage можно использовать для хранения информации таким способом, который переживёт перезагрузку страницы. Первый сохраняет данные навсегда (ну или пока пользователь специально не сотрёт их), а второй – до закрытия браузера.
Упражнения
Верстак JavaScript
Сделайте интерфейс, позволяющий писать и исполнять кусочки кода JavaScript.
Сделайте кнопку рядом с , по нажатию которой конструктор Function из главы 10 будет обёртывать введённый текст в функцию и вызывать его. Преобразуйте значение, возвращаемое функцией, или любую её ошибку, в строку, и выведите её после текстового поля.
<textarea id="code">return "hi";</textarea> <button id="button">Поехали</button> <pre id="output"></pre> <script> // Ваш код. </script>
Автодополнение
Дополните текстовое поле так, что при вводе текста под ним появлялся бы список вариантов. У вас есть массив возможных вариантов, и показывать нужно те из них, которые начинаются с вводимого текста. Когда пользователь щёлкает по предложенному варианту, он меняет содержимое поля на него.
<input type="text" id="field"> <div id="suggestions" style="cursor: pointer"></div> <script> // Строит массив из имён глобальных перменных, // типа 'alert', 'document', и 'scrollTo' var terms = []; for (var name in window) terms.push(name); // Ваш код. </script>
Игра «Жизнь» Конвея
Это простая симуляция жизни на прямоугольной решётке, каждый элемент которой живой или нет. Каждое поколение (шаг игры) применяются следующие правила:
- каждая живая клетка, количество соседей которой меньше двух или больше трёх, погибает
- каждая живая клетка, у которой от двух до трёх соседей, живёт до следующего хода
- каждая мёртвая клетка, у которой есть ровно три соседа, оживает
Соседи клетки – это все соседние с ней клетки по горизонтали, вертикали и диагонали, всего 8 штук.
Обратите внимание, что правила применяются ко всей решётке одновременно, а не к каждой из клеток по очереди. То есть, подсчёт количества соседей происходит в один момент перед следующим шагом, и изменения, происходящие на соседних клетках, не влияют на новое состояние клетки.
Реализуйте игру, используя любые подходящие структуры. Используйте Math.random для создания случайных начальных популяций. Выводите поле как решётку из галочек с кнопкой «перейти на следующий шаг». Когда пользователь включает или выключает галочки, эти изменения нужно учитывать при подсчёте следующего поколения.
<div id="grid"></div> <button id="next">Следующее поколение</button> <script> // Ваш код. </script>
habr.com