Как создать свой собственный виджет в WordPress? Создание виджета для рабочего стола Сделать виджет вордпресс.

май 21 , 2016

Каждый раз подключая на своих сайтах готовое решение от сервисов вроде disqus или google-аналитики, я удивляюсь простоте интеграции достаточно сложного функционала. Поставил в код 3 строчки javascript-кода - и у тебя уже развернулся блок с комментариями. Еще 2 строчки - и доступна аналитика от гугла или яндекса. Конечно, никакого волшебства при этом не происходит, те самые 3 строчки кода подтягивают с удаленного сервера весь нужный код, и по сути разворачивают небольшое веб-приложение на страницах Вашего сайта. Но как это устроено внутри и как это сделать самому? Разобраться с этим было достаточно интересно, и в итоге у меня получился небольшой виджет, который работает именно по такой простой схеме встраивания и при этом еще выполняют некоторые полезные вещи. Далее подробности.

Зачем нужны виджеты?

Для этой цели хорошо подходят iframe-ы. Это фактически отдельные html-страницы, которые встраиваются в другие страницы, при этом не имея доступа к своему "родителю". То есть в iframe можно встроить наше веб-приложение, которое будет спокойно выполнять свою работу, не вмешиваясь в основной сайт. А что именно будет делать Ваш виджет, строить систему комментариев на странице, показывать прикольную игрушку или рисовать интерактивный рекламный баннер - дело исключительно Вашего вкуса и фантазии.

В этой статье на игрушку мы замахиваться не будем, а рассмотрим, как создать встраиваемый виджет для определения погоды. Конечно, для этого есть много различных погодных сервисов, но нам неинтересно воспользоваться готовым решением. Хочется создать простенький виджет своими руками, чтобы понять, как это вообще работает и в дальнейшем применить знания уже для каких-то полезных вещей. Заодно попутно освежим знания в нативном javascript и php.

Что будем делать?

Мы создадим виджет, который рисует форму с прогнозом погоды на завтра. В качестве примера возьмем только температуру, но как увидите дальше, легко можно будет добавить и другие данные. В виджете будет располагаться информация о температуре на завтра, раскрывающийся список с возможностью выбрать город. Кнопка Обновить будет отправлять запрос на сервер, который в свою очередь обращается на сторонний сервис для определения погоды и возвращает нам нужную инфу. Эти данные мы обрабатываем и возвращаем в браузер клиенту. Где уже клиентская часть виджета перехватывает информацию и выводит ее пользователю.


Здесь мы видим какую-то страницу, где рассказывается, что якобы мы умеем определять погоду. И демонстрируем нашим посетителям формочку, дабы они могли убедиться, что погоду действительно можно узнать прямо здесь.

Я не развлекался с версткой формы, цель статьи не в этом. В реальном мире мы, конечно же, создали бы симпатичную формочку, которая привлекала бы внимание.

Итак, вернемся. Люди узнают погоду, возможно, даже не задумываясь о том, что фактически пользуются другим сервисом. Но все довольны и счастливы, Вы получаете посетителей на свой сайт, клиенты - нужную информацию.

Здесь нужно небольшое уточнение: смысл виджетов в том, чтобы предоставлять уникальный, удобный, интересный функционал. Мы не даем в нашем примере какую-то особенную информацию. Погоду можно узнать где угодно. Но в познавательных целях, так как мы сами пока ничего не умеем делать, возьмем данные по погоде с сервиса Прогноз погоды в России и СНГ . Они любезно предоставляют бесплатный api, коим мы и воспользуемся.

По технологиям

Тоже ничего сложного. Про iframe я уже проговорился. javascript-код будем писать на vanillaJS, без единой дополнительной библиотеки. Даже без jQuery для манипуляции DOM. Наша цель еще состоит и в том, чтобы полученный виджет был максимально легковесным, и ни к чему тащить в браузер пользователя мешок дополнительных библиотек для облегчения своей работы. Поэтому вспомним, как работать с DOM и отправлять ajax-запросы на нативном javascript, и наши клиенты скажут нам спасибо. Серверная часть - пара десятков строк кода на php.

Пишем код. Создаем базовую страницу

Страницу, на которой будет располагаться наш будущий виджет. Напишем там пару строчек текста о том, какие мы классные в плане умения прогнозировать погоду на завтра. Это будет файл index.html - обычная html-страничка. В секции head напишем так:

Webdevkin. Демонстрация виджета Погода

В секции body вот так:

Что здесь из интересного? В файле css/style.css будем хранить стили для страницы (не для виджета!). И в нужном месте создаем iframe..html. Мы убираем у него границу и возможность скроллинга и задаем руками размеры виджета. Конечно, интереснее создать адаптивный, но до этого доберемся позже.

Стили для страницы, без особых изысков:

Body { font-family: Arial; font-size: 14px; } .wrapper { width: 960px; margin: 0 auto; } .weather-widget-container { margin: 30px 0; }

Заготовка для виджета

Виджет представляет из себя обычный html-документ. В чем отличие? Первое - мы не будем заморачиваться с лишними мета-тегами, потому как поисковикам наш виджет не нужен. И второе - и стили, и js-код мы напишем прямо в коде html-страницы. Нам это нужно, чтобы сделать загрузку виджета максимально быстрой, а уменьшение числа запросов к веб-серверу в этом нам поможет. Все, что нужно, мы загрузим одним файлом.

В секции head у нас будет такой код:

В секции body:

Рассмотрим эти блоки подробнее.

Разметка для виджета

Температура на завтра °C

Здесь обычная форма. Сверху небольшая панель, где мы будем выводить температуру. Дальше select с выбором города. Значения value у городов взяты с сервиса meteoservice.ru, где именно, расскажу позже, в разделе, где будем непосредственно получать данные о погоде. И в конце кнопка Обновить. Верстка у нас будет на классах, айдишники проставлены тем элементам, доступ к которым нужен из кода javascript. Префикс wbd- (от webdevkin) используется для удобства, чтобы не путать разметки виджета и основной страницы.

Стили для виджета

html, body, body * { margin: 0; padding: 0; } .wbd-widget, .wbd-widget * { box-sizing: border-box; font-family: Ubuntu; } .wbd-widget { border: solid 1px #333; padding: 20px; color: black; } .wbd-widget__info { color: steelblue; font-size: 16px; text-align: center; } .wbd-widget__form-label { display: block; line-height: 30px; }

Стили для виджета максимально просты - Вы можете написать их под себя, как угодно. Не забываем, что стили ставим прямо в html-файл виджета в раздел head - style.

javascript-код виджета.

Напишем класс, в котором будут методы инициализации, привязки событий и получения данных с сервера. Не забываем, что код будем писать на нативном js, так как не хотим обременять пользователей лишним грузом библиотек.

Var WeatherWidget = (function() { // Для выполнения ajax-запросов var XHR = ("onload" in new XMLHttpRequest()) ? XMLHttpRequest: XDomainRequest; // Конструктор виджета function Widget() { this..php"; this.ui = { updateBtn: null, citySelect: null, temperatureSpan: null }; this.init(); } // Обновление данных о погоде Widget.prototype._updateData = function(e) { // Отправка ajax-запроса на сервер } // Инициализация компонентов ui Widget.prototype._initUI = function() { this.ui.updateBtn = document.getElementById("wbd-widget-update"); this.ui.citySelect = document.getElementById("wbd-widget-city"); this.ui.temperatureSpan = document.getElementById("wbd-widget-temperature"); } // Привязывание событий Widget.prototype._bindHandlers = function() { this.ui.updateBtn.addEventListener("click", Widget.prototype._updateData.bind(this)); } // Инициализация виджета Widget.prototype.init = function() { this._initUI(); this._bindHandlers(); this._updateData(); } // Возвращаем класс виджета return Widget; })(); new WeatherWidget();

Что здесь происходит? Мы создаем модуль на основе замыкания WeatherWidget, внутри оного пишем класс Widget, в прототип которого закидываем нужные методы и возвращаем его из замыкания. Последней строкой мы создаем экземпляр виджета - new WeatherWidget();

Переменная XHR нужна для выполнения ajax-запросов. В конструкторе инициализируем свойство url, по которому будем получать данные о погоде. Также есть объект ui, в котором хранятся 3 поля - те самые элементы DOM, к которым нам нужен доступ из js-кода. Инициализируются они позже, в методе _initUI(). Метод init() вызывает инициализацию ui, привязку событий и обновление данных с сервера (мы же хотим, чтобы при отрисовке виджета пользователь сразу видел погоду без нажатия на Обновить). В _bindHandlers привязывается метод _updateData к клику на кнопку Обновить. Это единственная "интерактивная" часть нашего виджета.

Обратите внимание на конструкцию Widget.prototype._updateData.bind(this). Здесь явным образом привязываем контекст - нам нужно, чтобы в методе _updateData this всегда указывал на экземпляр класса Widget. Сейчас будет видно, зачем - рассмотрим код метода _updateData

Получение данных с сервера, метод _updateData

// Обновление данных о погоде Widget.prototype._updateData = function(e) { e && e.preventDefault(); var xhr = new XHR(), city = this.ui.citySelect.value, temperatureSpan = this.ui.temperatureSpan, data = "city=" + city, resp; xhr.open("POST", this.url, true); xhr.setRequestHeader("Content-Type", "application/x-www-form-urlencoded"); xhr.send(data); xhr.onreadystatechange = function() { if (this.readyState != 4) return; if (this.status != 200) { console.log("Request error"); return; } resp = JSON.parse(this.responseText); temperatureSpan.innerHTML = resp.temperature; } }

Обращаю внимание, что в параметры метода передаем свойство e (event). Оно нужно, чтобы сделать preventDefault в самом начале, дабы не перезагрузить наш виджет (иначе сработает submit формы).
Но делаем мы это такой строчкой
e && e.preventDefault();
Эта дополнительная проверка на наличие параметра e нужна, потому что когда мы вызываем this._updateData(), параметр e будет равен undefined, и соответственно e.preventDefault() выкинет исключение.

После этого мы создаем нужные переменные, объект для ajax-запроса, выбранный город и DOM-элемент, в который выводим значение температуры, полученной с сервера. data будет отправляться в ajax-запросе, resp - это ответ от сервера. Дальше мы открываем соединение и отправляем данные на сервер. Дожидаемся ответа 200 от сервера и выводим полученную температуру в span. Условимся, что от сервера приходит json-строка в формате {"code": "success", "temperature": "диапазон температур"}. Традиционно обработку ошибок оставлю на Вашу совесть, все делают по-разному. И наконец, нам осталось узнать, как получить данные о погоде с нашего сервера.

Как узнавать погоду?

Рекомендую пользоваться этим сервисом с осторожностью. Когда статья уже почти была готова, неожиданно поменялся формат ответа по запросу о погоде. Отрубился вывод прогноза по времени суток, который я изначально хотел продемонстрировать в виджете. Пришлось частично переписывать код и уменьшать функциональность виджета, что меня не порадовало. Не знаю, как часто происходят у них такие вещи, но пользоваться сервисом в реальном приложении не советую.

Пишем php-код для получения информации о погоде

Как брать данные, уже понятно, алгоритм прост: вытаскиваем из $_POST параметр city - выбранный город, формируем строку вида http://xml.meteoservice.ru/export/gismeteo/point/$cityId.xml. Это путь к файлу с погодой. Отправляем на него get-запрос curl-ом. Полученный ответ парсим и вытаскиваем из него нужные параметры: минимальная и максимальная температуры. Полученные числа отдаем в json-объекте обратно в браузер.

$cityId = (int)$_POST["city"]; $url = "http://xml.meteoservice.ru/export/gismeteo/point/$cityId.xml"; $temperature = ""; if ($curl = curl_init()) { curl_setopt($curl, CURLOPT_URL, $url); curl_setopt($curl, CURLOPT_RETURNTRANSFER, true); $result = curl_exec($curl); curl_close($curl); $xml = simplexml_load_string($result); $object = $xml->REPORT->TOWN->FORECAST->TEMPERATURE; $temperature = $object["min"] . "-" . $object["max"]; } echo json_encode(array("code" => "success", "temperature" => $temperature));

Поясню про simplexml_load_string - эта функция создает xml-объект, который мы уже можем парсить. А создается объект из строки xml, которую мы получаем от сервиса погоды.
REPORT->TOWN->FORECAST->TEMPERATURE - это путь по узлам xml, чтобы добраться до нужных значений температуры. Пройдите по ссылке выше (московская погода) и наглядно увидите эти пути.
Если что-то непонятно, спрашивайте в комментариях.

Итого

И на этом все! Мы создали несложный виджет для получения информации о погоде. Главная его особенность в том, что его очень легко встроить на любой сайт, достаточно всего лишь вставить в html-код такие строки

Полагаю, что есть масса вариантов применения таких виджетов, от сбора различной информации до рекламных баннеров. А у Вас есть идеи, где это можно применить? Поделитесь в комментариях!

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

Чисто технически, виджет WordPress – это, так же как и плагин, набор файлов, которые копируются в определённую папку на сайте. В этих файлах задаются специальные инструкции для “движка”, благодаря которым система распознает сам факт виджета и позволяет его разместить в той или панели виджетов (число панелей и места их расположения зависят от конкретной WordPress-темы).

Система виджетов WordPress

В WordPress присутствуют мощные инструменты, позволяющие гибко управлять виджетами (добавлять на сайт, удалять, изменять их расположение). Для этого существует отдельный админ-раздел – Внешний вид -> Виджеты .

В левой части окна располагаются доступные к отображению виджеты, а в правой – панели виджетов. Добавить виджет на панель довольно просто. Для этого его следует просто перетащить в нужное место.

Как создать виджет в WordPress

“Движок” WordPress поставляется с целым набором различных виджетов. Но часто их функциональности бывает недостаточно для решения тех или иных задач. Поэтому и возникает необходимость создать свой, который будет отвечать всем требованиям.

Создание виджетов в WordPress подразумевает наличие навыков программирования на популярном скриптовом языке PHP , предназначенного для веб-разработки. В этом материале мы не будем детально рассматривать синтаксис языка, так как это уже отдельная тема. Мы лишь коснемся тех его конструкций, которые необходимы для успешного создания виджета.

В системе WordPress создать виджет можно двумя способами. Первый заключается в создании отдельного плагина, после активации которого будет доступен виджет для использования. Мы же воспользуемся более легким способом – добавим код виджета непосредственно в основной конфигурационный файл темы – functions.php .

Если Вы не знаете, как редактировать functions.php , то в этом случае Вам поможет плагин ProFunctions .

Разработка виджета

Для примера создадим самый простой виджет, который будет выводить название и описание сайта.

Для создания виджетов в WordPress применяется объектная модель программирования языка PHP . В “движке” имеются все необходимые инструменты для этого. Так, для виджетов существует специальный класс WP_Widget , использование которого и позволит успешно создать необходимый виджет для сайта WordPress. Он включает около 20 различных методов. Однако нам потребуются лишь четыре из них:

  • __construct() – регистрация базовой информации о виджете;
  • widget() – вывод виджета в области виджетов на сайте;
  • form() – параметры виджета, отображаемые в области администрирования WordPress;
  • update() – обновление настроек виджета в админ-панели.

В дополнение к этим четырем методам используется функция add_action() , необходимая для привязки пользовательской функции виджетов к специальному хуку widgets_init .

Рассмотрим поэтапно создание нашего виджета.

Во-первых, необходимо создать свой класс, который будет наследовать вышеуказанные методы основного класса WP_Widget .

Class wpschool_example_widget extends WP_Widget { }

В этом коде наш класс имеет название wpschool_example_widget . Директивой extends мы даем понять системе, что он будет наследовать все методы основного класса WP_Widget .

На следующем этапе добавим первый метод – __construct() . Он используется для назначения идентификатора, заголовка, имени класса и описания для виджета.

Public function __construct() { $widget_options = array("classname" => "wpschool_widget", "description" => "Это наш первый виджет",); parent::__construct("wpschool_widget", "WPSchool Widget", $widget_options); }

Чтобы понять эту функцию, следует начать с строки, начинающейся с parent::__ construct() . Эта строка создает новый виджет с идентификатором wpschool_widget , именем WPSchool Widget и двумя параметрами виджетов: имя класса (wpschool_widget ) и краткое описание (Это наш первый виджет ).

Весь этот код входит в wpschool_example_widget и используется для регистрации виджета в WordPress, а затем отображает заголовок и описание виджета в области администратора.

Следующий метод, который мы добавим, будет widget() . Он позволит вывести виджет в области виджетов на сайте.

Public function widget($args, $instance) { $title = apply_filters("widget_title", $instance[ "title" ]); $blog_title = get_bloginfo("name"); $tagline = get_bloginfo("description"); echo $args["before_widget"] . $args["before_title"] . $title . $args["after_title"]; ?>

Site Name:

Tagline:

Метод widget() содержит код, который генерирует фактический контент, отображаемый виджетом на сайте. В нашем примере мы предоставим пользователям возможность отображать, кроме названия и описания сайта, еще и заголовок самого виджета. Поэтому для этого нужно будет захватить этот заголовок, а затем использовать get_bloginfo() , чтобы отобразить название и описание блога.

Также следует понять еще кое-какие моменты.

Переменная $args содержит массив аргументов, которые могут использоваться при построении вывода виджета. Значения, содержащиеся в $args , задаются активной темой при регистрации области боковой панели.

$instance – это переменная, в которую загружаются значения, связанные с текущим экземпляром виджета. Если Вы добавили виджет на боковую панель дважды, каждый экземпляр $instance будет содержать значения, специфичные для каждого экземпляра виджета.

Фильтр widget_title возвращает заголовок текущего экземпляра виджета.

get_bloginfo() – функция, которая может использоваться для возврата всех видов метаданных WordPress-сайт, включая его название и описание.

После определения нескольких переменных, используя информацию из приведенного выше списка, код в примере продолжает формировать фактический вывод контента, который состоит из информации из переменной $args , заголовка, названия и описания сайта.

Обратите внимание, что практически каждый виджет должен включать аргументы before_widget , after_widget , before_title и after_title . Они необходимы для обеспечения того, чтобы каждый виджет был вложен в специфичные для темы теги HTML .

На следующем этапе добавим метод form() , позволяющий сохранять параметры виджета, отображаемые в админ-панели WordPress.

Public function form($instance) { $title = ! empty($instance["title"]) ? $instance["title"] : ""; ?>

" name="get_field_name("title"); ?>" value="" />

Для виджетов, имеющих множество разнообразных настроек, этот метод будет содержать довольного много сложного кода. Тем не менее, в нашем примере нужно лишь позволить пользователям задавать имя виджета, которое будет отображаться на сайте.

В методе form() возвращаются текущие значения конкретного экземпляра виджета, вызывая параметр $instance . Затем происходит проверка текущей информации об экземпляре, чтобы узнать, является ли заголовок пустым. Если это не так, будет выведено текущее название.

Следующий на очереди – метод update() , отвечающий за обновление настроек виджета в админ-панели.

Public function update($new_instance, $old_instance) { $instance = $old_instance; $instance[ "title" ] = strip_tags($new_instance[ "title" ]); return $instance; }

Видно, что метод принимает два параметра: $new_instance и $old_instance . Первый содержит значения, добавленные в форму настроек виджетов. Второй содержит существующие настройки (если таковые существуют).

Метод update() должен соответствующим образом проверять новые параметры, а затем назначать их переменной $instance и возвращать эту обновленную переменную.

Заключительным этапом создания нового виджета будут его регистрация и активация.

Function wpschool_register_widget() { register_widget("wpschool_example_widget"); } add_action("widgets_init", "wpschool_register_widget");

Тут, во-первых, создается функция для регистрации виджета, используя имя объекта виджета для его идентификации. Затем идет привязка функции регистрации к WordPress, используя хук widgets_init .

Отметим, что эта часть кода добавляется за пределы класса wpschool_example_widget . Когда он будет вызван, он подтянет виджет с соответствующим именем и запустит весь код, содержащийся в методах класса.

После добавления всего кода в файл functions.php в админ-разделе Внешний вид -> Виджеты должен появится виджет с названием WPSchool Widget , который теперь доступен для добавления на панель виджетов Вашей темы.

Полный текст нашего виджета:

/* Виджет WPSchool Widget */ class wpschool_example_widget extends WP_Widget { // Установка идентификатора, заголовка, имени класса и описания для виджета. public function __construct() { $widget_options = array("classname" => "wpschool_widget", "description" => "Это наш первый виджет",); parent::__construct("wpschool_widget", "WPSchool Widget", $widget_options); } // Вывод виджета в области виджетов на сайте. public function widget($args, $instance) { $title = apply_filters("widget_title", $instance[ "title" ]); $blog_title = get_bloginfo("name"); $tagline = get_bloginfo("description"); echo $args["before_widget"] . $args["before_title"] . $title . $args["after_title"]; ?>

Site Name:

Tagline:

" name="get_field_name("title"); ?>" value="" />

Операционная система Аndroid имеет множество функций и возможностей. Одной из них являются виджеты - окошки, которые позволяют использовать часть функционала приложения, без его запуска.

В основном виджеты идут в комплекте с приложением. Однако есть программы, которые лишены данной опции. А значит, нужно брать дело в свои руки!

  • С помощью Play Market скачиваем бесплатное приложение “KWGT Kustom Widget Maker”, которые можно приобрести бесплатно, однако часть функций будут доступны только после покупки дополнения.

Программа выступает в качестве платформы для запуска сторонних виджетов от разных разработчиков. Помимо этого вы можете изменить внешний вид виджетов, задать им дополнительный функционал.


Сперва можно подумать, что “KWGT Kustom Widget Maker” сложное приложение, которое напоминает программы для разработки софта. И да и нет: интерфейс похож, но сложного тут ничего нет.


Чтобы начать редактировать виджеты:

  • заходим на рабочий стол и вызываем меню редактирования рабочих столов путем удержания кнопки меню или долгим тапом по экрану;
  • находим рамку виджетов “KWGT” и выставляем необходимый размер, например - 4х2. После этого на рабочем столе образуется окошко;
  • Кликаем по окошку, тем самым открывая меню выбора виджетов;
  • Выбираем понравившийся макет и нажимаем на него (Дополнительные макеты можно скачивать с Play Маркет. Для этого в строке поиска приложений указываем “KWGT виджеты”);
  • После выбора понравившегося макета приложение перейдет к его редактированию. Будут доступны следующие настройки:
  1. Элементы, отвечающие за настройку геометрических параметров виджета;
  2. Фон, отвечающий за фоновую картинку на виджета;
  3. Касание, задающий действия которые будут выполняться при активации виджета;
  4. Слой, отвечающий за масштаб виджета;

В итоге мы получим уникальный виджет, с необходимым функционалом.

Для того чтобы сделать виджет в Android вовсе не обязательно уметь программировать. Есть несколько приложений-конструкторов, которые позволяют легко нарисовать виджет и дать ему нужный функционал.

Minimalistic Text

Приложение позволяет создавать минималистичные виджеты, состоящие из текста и чисел. Несмотря на название, у таких виджетов есть весьма широкие возможности.

После установки добавьте на рабочий стол виджет Minimalistic Text требуемого размера. Откроется окно настройки виджета.

В настройках можно выбрать фон, ориентирование, шрифт, действие по клику и т.д. Также в настройках есть предопределенные макеты для наполнения:

  • Время.
  • Дата.
  • Уровень заряда.
  • Температура.

Дополнительные возможности по наполнению виджета доступны при создании своего собственного макета виджета:

  • Текст.
  • Свободное/занятое место на карте SD.
  • Время работы системы.
  • Количество переданных данных по мобильной сети и не только.
  • Название сети Wi-Fi, IP адрес в сети Wi-Fi.
  • Количество занятой оперативной памяти.

Все величины можно выводить в тексте и в цифрах.

Ultimate custom widget (UCCW)

Данное приложение позволяет делать виджеты не только из текста, но и с графическим содержанием.

При запуске открывается окно создания виджета. Чтобы добавить на виджет объект нажмите кнопку +/- вверху. Чтобы всяким образом перемещать и редактировать его нажмите вверху на кнопку "Select Object" и выберите добавленный объект.

На виджетах можно размещать такие объекты:

  • Время, дату и день недели.
  • Аналоговые часы.
  • Пользовательский текст.
  • Уровень заряда в цифрах или же графическое отображение оного.
  • Всю информацию о погоде - температуру, влажность, скорость ветра и т.д.
  • Геометрические фигуры.
  • Картинки.
  • Количество непрочитанных писем Gmail, sms и пропущенных звонков.
  • Время, когда зазвонит будильник.

Каждый элемент можно вращать, растягивать, сгибать и менять ему цвет. Разумеется, можно настроить действие по клику (Select Object->Hotspots). Поддерживается импорт и экспорт созданных виджетов.

Недавно мне понадобилось создать гаджет для Windows Sidebar. Навыков в этом у меня не было, поэтому, немного погуглив и почитав документацию , приступаем.

Сразу покажу то, что получилось в итоге


Гаджет будет получать информацию с сайта в виде xml, парсить и, собственно, отображать. Также гаджет будет проверять наличие новых версий, и в случае их присутствия, отказываться работать:)
Изначально, ради получения опыта, хотел написать гаджет полностью на VBScript (так как с ним еще не имел дела), но в конечном итоге пришлось делать вставки на JavaScript.
Перейдем непосредственно к коду. Весь код здесь я рассматривать не буду, покажу лишь основные моменты. Ссылка на готовый гаджет – в конце статьи.
Главный файл гаджета – его манифест – файл Gadget.xml. Он должен называться именно так и располагаться в корне нашего архива (гаджет есть ни что иное, как архив ZIP с расширением.gadget).

Weather from Info.Denms.Ru 1.0.1232 Full Weather Widget (Info.Denms.Ru)

Рассмотрим его более подробно.
Элемент должен содержать apiVersion, равный 1.0.0 (на данный момент), а также атрибут src, в котором указан главный файл нашего гаджета;
Разрешения для гаджета. Устанавливаем равным full;
Минимальная версия Widows Sidebar. На данный момент – 1.0;
Параметры - имя гаджета, - версия, - информация об авторе, - ссылка на страницу с гаджетом, - иконка гаджета и будут отображаться на панели установленных гаджетов.

Файл main.html – обычный html файл, приводить его полностью не буду, остановлюсь лишь на некоторых моментах.
С помощью элемента g:background задается фон гаджета. Сделаем его прозрачным.

Гаджет может находиться в двух состояниях – docked (слева на скрине выше), и undocked (справа). Будем хранить текущее состояние гаджета в переменной JavaScript docked.

Функция-обертка isDocked потребуется нам в дальнейшем, чтобы из VBScript узнать текущее состояние гаджета (как я не старался, но реализовать это на чистом VBScript не смог). Еще одно замечание – скрипты корректно работают именно в этом порядке, т.е. сначала описываем скрипты VBScript, потом JavaScript.

Остальные элементы в main.html представлены элементами DIV с абсолютным позицированием. Впоследствии из скриптов мы будем обращаться к ним по их id.

С помощью JavaScript зададим состояния docked и undocked для гаджета, а так же укажем файл настроек (main.js)

System.Gadget.onDock = resize; System.Gadget.onUndock = resize; System.Gadget.settingsUI = "settings.html"; System.Gadget.onSettingsClosed = SettingsClosed; docked=0; //начальное состояние гаджета resize(); //инициализация

Как видно из листинга выше, при смене состояний гаджета будет вызываться функция resize().

Function resize() { bd = document.body.style; System.Gadget.beginTransition(); if (System.Gadget.docked) { // small state bd.width=148; //устанавливаем размеры гаджета bd.height=201; docked = 1; bd.background="url(images/gadget.png) no-repeat"; //устанавливаем фон //далее следует перенос значений из состояния undocked в docked и обнуление элементов для состояния undocked document.getElementById("small_needupdate").innerHTML = document.getElementById("big_needupdate").innerHTML; document.getElementById("big_needupdate").innerHTML = ""; //... } else { // big state bd.width=230; bd.height=160; bd.background="url(images/gadgeth.png) no-repeat"; docked=0; //перенос значений из состояния docked в undocked и обнуление элементов для состояния docked document.getElementById("big_needupdate").innerHTML = document.getElementById("small_needupdate").innerHTML; document.getElementById("small_needupdate").innerHTML = ""; //... } System.Gadget.endTransition(System.Gadget.TransitionType.morph,1); }

Также можно описать функцию сохранения настроек. В моем гаджете их нет, но для примера покажу как это делается

Function SettingsClosed(event) { if (event.closeAction == event.Action.commit) { //alert System.Gadget.Settings.readString("test"); } }

ReadString – читает ранее сохраненную строку, writeString, соответственно, записывает.
Методы System.Gadget.beginTransition(); и System.Gadget.endTransition(); нужны для “плавного» изменения размера гаджета. В Windows Seven они игнорируются , но я все же оставил их для обратной совместимости.

Как уже говорилось выше, сервер предоставляет нам информацию о погоде в формате xml.

1.7 41 пасмурно снег 87 Ю-З 5 -3 -1 -1 26 1 -9 41 0 …

Скачивать и парсить xml будем на VBScript.

Sub DownloadXML2 Set objXML = CreateObject("Microsoft.XmlHttp") objXML.Open "GET", "http://info.kovonet.ru/weather.xml", True objXML.OnReadyStateChange = GetRef("objXML_onreadystatechange") objXML.setRequestHeader "If-Modified-Since", "Sat, 1 Jan 2000 00:00:00 GMT" objXML.Send iTimeoutID = window.SetTimeout("mySleep", 1000) End Sub

Функция mySleep будет проверять наше соединение на таймаут.

Sub mySleep if bRespReceived = "false" then "ответ еще не получен iTimeout = iTimeout + 1 if (iTimeout > 30) then "таймаут timerFirstRun = window.SetTimeout("Update", 60000) "попытка повторного обновления через минуту else "таймаут еще не достигнут, продолжаем считать секунды iTimeoutID = window.SetTimeout("mySleep", 1000) end if end if End Sub

В случае успешного скачивания objXML.readyState будет равен четырем, а статус (objXML.status) вернет значение 200.

Function objXML_onreadystatechange() If (objXML.readyState = 4) Then "msgbox objXML.statusText If (objXML.status = 200) Then bRespReceived=true SaveFile(objXML.responseText) else timerFirstRun = window.SetTimeout("Update", 60000) "попытка повторного обновления через минуту End If End If End Function

В этом случае сохраняем файл во временную папку Windows

Function SaveFile(what) Set fso = CreateObject("Scripting.FileSystemObject") tempFolder = fso.GetSpecialFolder(2) filepath = tempFolder+"\weather.xml" Dim fso1, tf Set fso1 = CreateObject("Scripting.FileSystemObject") Set tf = fso1.CreateTextFile(filepath, True, True) "rewrite, unicode tf.Write(what) tf.Close ParseXML End Function

И начинаем парсить файл.

Sub ParseXML Set fso = CreateObject("Scripting.FileSystemObject") tempFolder = fso.GetSpecialFolder(2) filepath = tempFolder+"\weather.xml" Set xmlDoc = CreateObject("Msxml2.DOMDocument") xmlDoc.async="false" xmlDoc.load(filepath) "главная нода – в нашем случае Set currNode = xmlDoc.documentElement "дни недели – Set dayNode = currNode.firstChild While Not dayNode Is Nothing Set currNode = dayNode.firstChild While Not currNode Is Nothing if currNode.parentNode.getAttribute("id") = "today" then "сегодняшний день if currNode.nodeName = "temp" then document.getElementById(prefix+"maintemp").innerHTML = currNode.childNodes(0).text+Chr(176) "отображаем остальные элементы Else "не сегодняшний день, отображаем более мелко "... end If Set currNode = currNode.nextSibling Wend Set dayNode = dayNode.nextSibling Wend End Sub

Проверка на новые версии производится точно таким же способом.
Не забываем создать файл настроек - settings.html, о существовании которого мы объявили выше.

Настройки

Вот, собственно, и все. Буду рад, если моя (первая:)) статья оказалась кому-то полезной.

Использованные источники.