php[world] 2018 - Call for Speakers

PHP и HTML

PHP и HTML тесно взаимодействуют: PHP может генерировать HTML, а HTML может передавать информацию PHP. Перед чтением вопросов в этом разделе важно чтобы вы понимали как получать переменные извне PHP. Страницы руководства по этой теме содержат много примеров.

Какое кодирование/декодирование я должен выполнять при передаче значения через форму/URL?

Здесь несколько этапов, на которых кодировка важна. Предположим, что у вас есть $data типа string, содержащая строку, которую вы хотите передать без кодирования. Вот эти этапы:

  • Интерпретация HTML. Для того, чтобы задать произвольную строку, вы должны заключить её в двойные кавычки и использовать htmlspecialchars() для кодирования.

  • URL: URL состоит из нескольких частей. Если вы хотите чтобы ваши данные были восприняты как один элемент, вы должны закодировать их с помощью urlencode().

Пример #1 Скрытый элемент HTML-формы

<?php
    
echo '<input type="hidden" value="' htmlspecialchars($data) . '" />'."\n";
?>

Замечание: Использовать urlencode() для $data неправильно, так как кодировать данные в urlencode() это обязанность браузера. Все популярные браузеры делают это правильно. Отметьте, что это происходит вне зависимости от метода (например, GET или POST). Вы заметите это только в случае GET-запроса, так как POST-запросы обычно скрыты.

Пример #2 Данные, редактируемые пользователем

<?php
    
echo "<textarea name='mydata'>\n";
    echo 
htmlspecialchars($data)."\n";
    echo 
"</textarea>";
?>

Замечание: Данные показываются браузером как предполагается, потому что браузер будет интерпретировать экранированные HTML-символы. При отправке через GET или POST данные будут закодированы (urlencoded) браузером для передачи и декодированы (urldecoded) PHP. Поэтому вам не надо выполнять какое-либо кодирование/декодирование url самостоятельно, всё обрабатываются автоматически.

Пример #3 В URL

<?php
    
echo '<a href="' htmlspecialchars("/nextpage.php?stage=23&data=" .
        
urlencode($data)) . '">'."\n";
?>

Замечание: На самом деле вы подделываете HTML GET-запросом, поэтому необходимо вручную закодировать (urlencode()) данные.

Замечание: Вам надо применить htmlspecialchars() ко всему URL, потому что URL появляется как значение HTML-атрибута. В этом случае, браузер сначала раскодирует всё значение (обратная операция htmlspecialchars()) и затем передаст URL. PHP поймёт URL правильно, так как вы закодировали данные с urlencode(). Вы заметите, что & в URL заменяется на &amp;. Хотя большинство браузеров это исправляют, если вы забудете об этом, но все же это не всегда возможно. Поэтому, даже если ваш URL не динамический, вам надо закодировать его с помощью htmlspecialchars().

Я пытаюсь использовать <input type="image">, но переменные $foo.x и $foo.y недоступны. $_GET['foo.x'] тоже не существует. Где они?

При отправке формы, вместо стандартной кнопки отправки возможно использовать изображение с тэгом как:

<input type="image" src="image.gif" name="foo" />
Когда пользователь кликает где-либо на картинке, серверу будет послана сопутствующая форма с двумя дополнительными переменными: foo.x и foo.y.

Так как имена foo.x и foo.y не разрешены в PHP, они автоматически преобразуются в foo_x и foo_y. То есть, точки заменяются на подчёркивания. Таким образом, вы обращаетесь к этим переменным так же, как и к любым другим, описанным в разделе о получении переменных извне PHP. Например, $_GET['foo_x'].

Замечание:

Пробелы в именах переменных запроса преобразуются в подчёркивания.

Как создать массивы в HTML <form>?

Для того, чтобы результаты <form> были переданы вашему PHP скрипту как массив, именуйте элементы <input>, <select> или <textarea> следующим образом:

<input name="MyArray[]" />
<input name="MyArray[]" />
<input name="MyArray[]" />
<input name="MyArray[]" />
Заметьте квадратные скобки после имени переменной, это делает её массивом. Вы можете сгруппировать элементы в массив, присваивая одно и то же имя разным элементам:
<input name="MyArray[]" />
<input name="MyArray[]" />
<input name="MyOtherArray[]" />
<input name="MyOtherArray[]" />
Это создаст два массива, MyArray и MyOtherArray, которые будут переданы PHP-скрипту. Также возможно задать определенные ключи для ваших массивов:
<input name="AnotherArray[]" />
<input name="AnotherArray[]" />
<input name="AnotherArray[email]" />
<input name="AnotherArray[phone]" />
Массив AnotherArray теперь будет содержать ключи 0, 1, email и phone.

Замечание:

Определять ключи массивов в HTML необязательно. Если вы не установите ключи, массив заполняется в порядке появления элементов в форме. Наш первый пример будет содержать ключи 0, 1, 2 и 3.

Также смотрите Функции для работы с массивами и Переменные извне PHP.

Как получить все результаты из HTML-тега select с атрибутом multiple?

HTML-тег select с указанным multiple позволяет пользователю выбрать несколько элементов из списка. Эти элементы затем передаются обработчику формы. Проблема в том, что они все переданы с одним и тем же именем. Например:

<select name="var" multiple="yes">
Каждая выбранная опция поступит обработчику формы как:
var=option1
var=option2
var=option3
      
Каждая опция будет перезаписывать содержимое предыдущей переменной $var. Решение - воспользоваться возможностью PHP - "массив из элемента формы". Следует использовать следующее:
<select name="var[]" multiple="yes">
Это укажет PHP обрабатывать $var как массив и каждое присваивание значения в var[] добавит элемент в массив. Первым элементом будет $var[0], следующим - $var[1] и т.д. Функция count() может быть использована для определения, сколько элементов было выбрано, а функция sort() - для сортировки массива опций, если это необходимо.

Заметьте, что если вы используете JavaScript, то [] в имени элемента могут вызвать проблемы, если вы пытаетесь обращаться к элементу по имени. Вместо этого используйте числовой идентификатор элемента формы или заключите имя переменной в одинарные кавычки и используйте его как индекс массива элементов, например:

variable = document.forms[0].elements['var[]'];
      

Как я могу передать переменную из JavaScript в PHP?

Так как JavaScript является (обычно) клиентской технологией, а PHP, как правило, серверной, и поскольку HTML - протокол "без состояния", эти два языка не могут обмениваться переменными напрямую.

Однако, возможно передавать переменные между ними. Один из способов достичь этого - сгенерировать JavaScript-код из PHP и принудительно обновлять браузер, посылая определённые переменные обратно PHP-скрипту. Нижеприведенный пример показывает как это сделать - он позволяет PHP-коду получить высоту и ширину экрана, что, обычно, возможно только на стороне клиента.

Пример #4 Генерирование JavaScript из PHP

<?php
if (isset($_GET['width']) AND isset($_GET['height'])) {
  
// выводим переменные с размерами
  
echo "Ширина экрана: "$_GET['width'] ."<br />\n";
  echo 
"Высота экрана: "$_GET['height'] ."<br />\n";
} else {
  
// передаем переменные с размерами
  // (сохраняем оригинальную строку запроса
  //   -- post переменные нужно будет передавать другим способом)

  
echo "<script language='javascript'>\n";
  echo 
"  location.href=\"${_SERVER['SCRIPT_NAME']}?${_SERVER['QUERY_STRING']}"
            
"&width=\" + screen.width + \"&height=\" + screen.height;\n";
  echo 
"</script>\n";
  exit();
}
?>

add a note add a note

User Contributed Notes 3 notes

up
2
smileytechguy at smileytechguy dot com
4 months ago
The (at least that I've found) best way to pass data from PHP to JS is json_encode.  Doing so will convert arrays, strings, numbers, etc. as best as possible.

<?php
$myInt
= 7;
// a bunch of special characters to demonstrate proper encoding
$myString = <<<EOF
" ' ; &\ $
EOF;
$myArr = [1, "str", 2];
$myAssocArr = ["foo" => "bar"];
?>

<script>
var myInt = <?= json_encode($myInt) ?>;
var myString = <?= json_encode($myString) ?>;
var myArr = <?= json_encode($myArr) ?>;
var myAssocArr = <?= json_encode($myAssocArr) ?>;
</script>

This will render the following JS code, which correctly stores the variables:
<script>
var myInt = 7;
var myString = "\" ' ; &\\ $";
var myArr = [1,"str",2];
var myAssocArr = {"foo":"bar"};
</script>

Do note that there are no "s or anything like that around the json_encode output; json_encode handles that for you.
up
-12
jetboy
12 years ago
While previous notes stating that square brackets in the name attribute are valid in HTML 4 are correct, according to this:

http://www.w3.org/TR/xhtml1/#C_8

the type of the name attribute has been changed in XHTML 1.0, meaning that square brackets in XHTML's name attribute are not valid.

Regardless, at the time of writing, the W3C's validator doesn't pick this up on a XHTML document.
up
-24
Jay
4 years ago
If you have a really large form, be sure to check your max_input_vars setting.  Your array[] will get truncated if it exceeds this.  http://www.php.net/manual/en/info.configuration.php#ini.max-input-vars
To Top