Как подгрузить HTML-код из файла силами JavaScript на web-страницу через объект XMLHttpRequest?
Файл index.html обрабатывается силами web-сервера и автоматически загружается в браузер пользователя при обращении к сайту (главной странице).
Файл index.html имеет классическую разметку документа:
DOCTYPE html> html lang="ru"> head> meta charset="UTF-8"> meta name="viewport" content="width=device-width, initial-scale=1.0"> title>Документtitle> head> body> body> html>
Это «пустая» HTML-страница со своим уникальным адресом. На странице визуально нет ничего. Просто белый лист.
Задача
Необходимо на страницу index.html подключить HTML-разметку из файла text.html , но так чтобы файл text.html содержал только HTML-элементы и . То есть мы хотим подгрузить только уникальную информацию на страницу без «лишних» мета-данных.
Также мы хотим сделать эту загрузку в фоне, без перезагрузки страницы index.html . То есть пользователь не увидит в адресной строке браузера другого адреса. Перезагрузки страницы не будет.
Файл text.html имеет разметку:
ВНИМАНИЕ! Запросы к серверу мы будем делать ТОЛЬКО через работающий локально веб-сервер. Ознакомьтесь с протоколом CORS и стандартом Fetch. Локальный запуск файла index.html в браузере не приведёт к работающему результату. Используйте бесплатный продукт «OpenServer» для своих тестов.
Предпосылки. Зачем это нужно?
Главная идея задачи — это создание шаблонов генерации документов силами JavaScript, при помощи которых можно лучше управлять визуальным содержимым сайта.
Каждая отдельная страница сайта перестаёт быть статичной (уже собранной). В результате, мы разделяем потенциальную страницу на части. Например:
- Один документ отвечает за шапку сайта
- Другой за подвал
- Третий за основное содержимое
- Четвёртый за боковые панели
- Пятый за рекламные баннеры
- Шестой за галерею фотографий
- Седьмой за контактную информацию
- и т. п..
Решение задачи
Для начала подключим на страницу index.html файл со скриптом, который будет называться gettext.js .
В файле index.html внутри элемента поместим элемент с атрибутом src и его значением gettext.js
Для решения задачи мы будем использовать объект XMLHttpRequest. Стандарт XMLHttpRequest определяет API-интерфейс, который предоставляет клиенту функциональные возможности по сценарию для передачи данных между клиентом и сервером .
- Посылаем запрос на сервер.
- Дожидаемся ответа. Ловим содержимое файла.
- Вносим нужные изменения в документ.
Отредактируем файл gettext.js
var inBody = function()< // Создаём анонимную функцию. Помещаем её в переменную "inBody" var xhr = new XMLHttpRequest() // Создаём локальную переменную XHR, которая будет объектом XMLHttpRequest xhr.open('GET', 'text.html') // Задаём метод запроса и URL запроса xhr.onload = function()< // Используем обработчик событий onload, чтобы поймать ответ сервера XMLHttpRequest console.log(xhr.response) // Выводим в консоль содержимое ответа сервера. Это строка! document.body.innerHTML = xhr.response // Содержимое ответа, помещаем внутрь элемент "body" > xhr.send() // Инициирует запрос. Посылаем запрос на сервер. > inBody() // Запускаем выполнение функции получения содержимого файла
Логика работы объекта XMLHttpRequest
В первой строке мы создаём анонимную функцию и помещаем её в переменную «inBody«. Название переменной описывает решаемую задачу — дословно «вТело«. То есть результатом выполнения этой функции будет интеграция содержимого файла text.html внутрь элемента загруженной странице index.html на клиенте (в браузере)
Со второй строки начинается тело функции. С помощью конструктора объектов мы создаём новый объект XMLHttpRequest и помещаем его в локальную переменную «xhr«. Название переменной означает сокращённую запись от первых трёх букв — X ML H ttp R equest ( XHR ). Т.к. область видимости ограничена родительской функцией, то можно использовать подобное название без опасений. В рабочих проектах не рекомендую использовать глобальные переменные с именем XHR , т. к. на практике такое имя применяется в основном к объектам XMLHttpRequest.
Третья строка запускает метод open() объекта XMLHttpRequest. В этом методе задаётся HTTP-метод запроса и URL-адрес запроса. В нашем случае мы хотим получить содержимое файла по адресу «text.html», который находится в той же директории, что и загруженный в браузер index.html. Получать содержимое мы будем методом «GET» протокола HTTP.
Четвёртая строка описывает логику работы обработчика события onload. Пользовательский агент ДОЛЖЕН отправить событие load, когда реализация DOM завершит загрузку ресурса (такого как документ) и любых зависимых ресурсов (таких как изображения, таблицы стилей или сценарии). То есть обработчиком события onload мы ловим срабатывание типа события load и полученные ресурсы мы достаём при помощи атрибута ответа response объекта XMLHttpRequest.
Пятой строкой мы выводим в консоль результат ответа сервера. Она необходима для разработки. Она не обязательна. ВНИМАНИЕ! Содержимое ответа по-умолчанию имеет тип данных — string (строка). Это стандарт клиент-серверного взаимодействия. Все данные передаются по сети в виде «строковых данных». Так всегда происходит — это норма. Если вы точно знаете каким образом строка будет оформлена, тогда вы можете воспользоваться атрибутом ответа responseType и в этом случае содержимое ответа будет одним из:
- пустая строка (по умолчанию),
- arraybuffer
- blob
- document
- json
- text
В шестой строке мы присваиваем элементу внутренне содержимое пришедшее из файла на сервере. Это содержимое будет заключено между открывающим и закрывающим . XMLHttpRequest имеет связанный ответ response.
Восьмая строка инициирует запрос на сервер методом send() и отправляет его.
На десятой строке мы вызываем функцию «inBody»
Результат работы
Мы видим итоговую страницу с нужным нам содержимым. На favicon не обращаем внимания т. к. браузер Chrome вдруг решил его поискать.
Вкладка имеет название «Документ», которое пришло из элемента .
Главная страница нашего «воображаемого» сайта http://getinnerofpage/ содержит информацию, пришедшую из другого файла.
Разметка итогового документа после выполнения запроса к серверу. Браузер «переварил» строковые данные и преобразовал их в HTML-разметку.
В инструментах разработчика на вкладке Network мы видим последовательность загрузки данных для главной страницы сайта
Сперва браузер запросил HTML-документ главной страницы сайта. Статус 200 — ОК. Потом после разбора разметки браузер загрузил файл со скриптом. Статус 200 — ОК. После этого браузер начал синхронно обрабатывать выполнение инструкций файла скрипта. На восьмой строчке выполнения файла gettext.js мы видим обращение к файлу text.html
Статус 200 — ОК означает успешную подачу запроса — запрашиваемые ресурсы имеются на сервере.
В ответе сервера браузер уже понимает пришедшие данные и подсвечивает HTML-синтаксис, указывая на элементы и . То есть браузер уже сам разобрал пришедший тип данных string и подсветил разработчику открывающиеся и закрывающиеся элементы.
Важно обратить внимание, что на подгрузку данных «в фоне» потребовалось некоторое время. В реальных проектах нужно учитывать эту особенность и правильно распределять зависимости последовательностей отдачи содержимого пользователю.
Может оказаться так, что при формировании финансового графика часть данных не успеет прийти вовремя — это исказит трактование данных из отчёта и навредит бизнесу из-за ошибки вычислений. Будьте внимательны! В таких случаях уместно использовать объект Promise .
Динамическая загрузка контента через jQuery
В этом учебнике мы возьмем средний обычный веб-сайт и улучшим его с помощью jQuery. Мы добавим AJAX-функциональности, которая позволит содержимому динамически загружать контент, без перезагрузки страницы, в соответствующий контейнер. Вместо того, чтобы заставлять пользователя переходить на другую страницу. А также интегрируем кое-какие потрясающие анимационные эффекты.
Перед тем, как мы приступим к практическим шагам, я Вам рекомендую просмотреть демо-результат работы.
Для примера я сначала построил очень простой макет. Вот скриншот и HTML-код, который мы будем использовать.
Онлайн курс по JavaScript
Научитесь создавать приложения со сложными интерфейсами
Это основной язык для современной веб-разработки — почти 100% сайтов работает на JavaScript. Освойте его с нуля всего за 4 месяца, и вы сможете зарабатывать от 70 000 рублей.
ajax . nettuts
Welcome!
Шаг 1
Вначале пойдите и скачайте последний стабильный релиз jQuery и добавьте ссылку на него в ваш документ:
Как я считаю, одна из лучших черт jQuery – это его простота. Можно достичь поставленной задачи в сочетании с ошеломляющими эффектами всего несколькими строчками кода.
Во-первых, давайте загрузим библиотеку jQuery и запустим функцию, когда документ уже готов (когда DOM уже загружен).
Шаг 2
Нам нужно сделать так, чтобы при нажатии на ссылку в меню навигации на нашей странице, браузер не делал переход на соответствующую страницу, а динамически загружал контент этой страницы внутрь нашего макета, без перезагрузки.
Для этого нам нужно определить ссылки в меню навигации и запускать эту функцию при щелчке на них:
Давайте наметим, что мы должны сделать в этой функции по порядку.
Удалить содержимое текущей страницы.
Получить новое содержимое страницы и добавить в содержимое DIV.
Вначале нам нужно определить, из какой страницы получать данные после того, как на ссылку нажали. Все, что для этого нужно сделать – это получить атрибут ‘href’ нажатой ссылки и использовать его как адрес страницы, из которой будет загружаться информация.
Кроме того, к полученному URL необходимо добавить метку элемента, так как мы не собираемся использовать ВСЕ содержимое из запрашиваемой страницы. Вместо этого, нам требуются данные внутри разделителя div с меткой ‘content’:
Чтобы наглядно продемонстрировать, что делает вышеуказанный код, давайте представим, что пользователь нажимает на ссылку ‘about’ , которая связана со страницей ‘about.html’ – в этой ситуации переменной будет: ‘about.html #content’ – и это именно та переменная, которую мы будем запрашивать при простом вызове. Однако первое, с чего мы начнем – это создадим красивый эффект для содержимого текущей страницы. Вместо того, чтобы оно просто исчезало, мы используем функцию «скрывания» jQuery:
Указанная функция быстро «прячет» #content div, и как только эффект заканчивает свое действие, она, в свою очередь, инициирует функцию «loadContent» (загрузка нового содержимого [через ajax]) – это функция, которую мы определим позже (в шаге 4).
Шаг 3
Как только старое содержимое исчезнет с ошеломляющим эффектом, нам нельзя просто оставить пользователей в ожидании, пока не появится новое содержимое (особенно если у них медленное соединение с Интернетом), так что мы создадим немножко графики «загрузки» чтобы пользователи знали, что что-то происходит в фоновом режиме:
Вот CSS, прилагающаяся к свежесозданному #load div:
Таким образом область, которая должна содержать анимацию загрузки, первоначально не отображается. Далее, при инициализации функции fadeIn () (см. выше в коде), она начинает отображаться в верхнем правом углу сайта и показывает анимированный GIF, пока через некоторое время снова не исчезнет с экрана.
Шаг 4
Через некоторое время, когда пользователь нажмет на одну из ссылок, начнет происходить следующее:
Текущее содержание эффектно исчезает.
Появляется сообщение о загрузке.
А теперь давайте напишем ту самую функцию загрузки содержимого, о которой мы ранее говорили:
Функция loadContent вызывает запрошенную страницу, а когда это уже выполнено, вызывает функцию ‘showNewContent’ (показ нового содержимого):
Эта функция – showNewContent — использует функцию show() jQuery (на самом деле, это слишком скучное название для такого отличного эффекта) с тем, чтобы новое содержимое, помеченное меткой элемента ‘#content’ появилось на странице. Однажды вызванная, она инициирует функцию ‘hideLoader’ (исчезание):
Нам необходимо помнить, что функция обработки клика должна возвратить «false», чтобы браузер не совершил перехода на другую страницу.
Теперь все должно работать прекрасно. Пример этого можно увидеть здесь: [LINK]
Шаг 5
Можно было бы на этом и остановиться, но если вы беспокоитесь об удобстве использования (о котором должны заботиться), важно проделать еще кое-какую работу. Проблема нашего текущего решения в том, что оно игнорирует адреса URL. Что, если пользователь захочет определить ссылку на одну из наших так называемых «страниц»? Сейчас это сделать невозможно, потому что URL все время один и тот же.