Введение
Отобразить данные собственного модуля — пожалуй, это первое, что захочет сделать начинающий разработчик модулей для системы групповой работы TeamWox. В этой статье вы узнаете, как добавить новую страницу (представление данных) в модуль.
Для начала мы кратко рассмотрим, каким образом взаимодействуют между собой данные, их представление и действия пользователя. Затем мы создадим класс новой страницы и добавим его в проект модуля. Далее мы создадим новое правило перенаправления запросов, которое свяжет новую страницу с модулем. Затем мы вызовем новую страницу через главное меню модуля. В конце статьи мы кратко рассмотрим базовый функционал шаблонов — мощного средства вывода данных на страницах.
Архитектура модуля TeamWox
Model View Controller (MVC) — это популярная архитектура программного обеспечения (шаблон проектирования, design pattern), в котором модель данных приложения (Model, модель), пользовательский интерфейс (View, представление) и управляющая логика (Controller, контроллер) разделены на три отдельных компонента. При этом модификация одного из компонентов оказывает минимальное воздействие на другие компоненты.
Архитектура модуля TeamWox — это модифицированный вариант MVC. В TeamWox термины MVC называются несколько иначе, однако сути это не меняет.
| Термин архитектуры MVC | Термин TeamWox |
|---|---|
| Модель | Менеджер |
| Представление | Страница |
| Контроллер | Модуль |
Рассмотрим как устроена архитектура модуля и каким образом взаимодействуют между собой его основные структурные единицы:

Взаимодействие между Модулем (Controller), Менеджером (Model) и Страницами (View)
- HTTP-запрос поступает в Модуль, который выбирает нужную Страницу для обработки этого запроса.
- Страница обрабатывает запрос и обращается за данными к Менеджеру.
- Менеджер отдает обработанные данные обратно в Модуль, который предоставляет интерфейс доступа к этим данным через Страницы. Страницы через Модуль отправляют обработанные данные в виде HTTP-ответа для отображения в окне браузера.
Структура папок и файлов модуля HelloWorld
Рассмотрим реализацию описанной выше концепции на практике. В статье TeamWox SDK: Как добавить готовый модуль в TeamWox вы узнали, как легко скомпилировать готовый модуль Hello World. Продолжим работу с этим модулем и рассмотрим подробнее структуру его папок и файлов.
Модуль Hello World расположен в папке <папка_установки_TeamWox SDK>\Modules\HelloWorld. В корневой папке находятся исходные коды Модуля. В подпапке \Managers находятся исходные коды менеджера, а в папке \Pages — исходные коды всех страниц модуля.
Добавление новой страницы в проект Visual Studio
Добавьте в проект страницу, которая будет отображать обычный текст. Откройте проект HelloWorld, с которым мы работали в прошлой статье. Добавим класс СPageNumberThree, отвечающий за отображение новой страницы Page 3 (две страницы в модуле уже есть, пусть будет третья). Относительная ссылка на новую страницу будет /helloworld/number_three.
Класс страницы состоит из заголовочного файла (.h) с описанием класса, и файла исходного кода (.cpp) с его реализацией. Страницы, согласно принятой структуре проекта, должны находиться во вложенной папке \Pages относительно корневой папки HelloWorld\ нашего модуля.
Откройте проект
HelloWorld.vcproj, раскройте в нем папкуHeader Files\Pages, щелкните правой кнопкой мыши и выберитеAdd
New Item.Выберите шаблон
Header File (.h), задайте имяPageNumberThree. В полеLocationукажите папку<папка_установки_TeamWox SDK>\Modules\HelloWorld\Pages\(в этой папке на диске будет находиться файл) и нажмитеAdd.Аналогичным образом, но уже в папке
Source Files\Pages, создайте файл исходного кода (.cpp) страницы с тем же именемPageNumberThree.
Добавление класса новой страницы
Добавим исходный код необходимого нам класса в созданные файлы. При этом мы воспользуемся исходным кодом других страниц модуля в качестве шаблона.
1. В файле PageNumberThree.h объявите класс CPageNumberThree для новой страницы. Используя заголовочный файл первой страницы PageNumberOne.h в качестве шаблона, отредактируйте его следующим образом (изменения выделены желтым):
//+------------------------------------------------------------------+ //| TeamWox | //| Copyright © 2006-2008, MetaQuotes Software Corp. | //| https://www.metaquotes.net | //+------------------------------------------------------------------+ #pragma once //+------------------------------------------------------------------+ //| Page 3 | //+------------------------------------------------------------------+ class CPageNumberThree : public CPage { private: IServer *m_server; public: CPageNumberThree(); ~CPageNumberThree(); //--- обработчик TWRESULT Process(const Context *context,IServer *server,const wchar_t *path); //--- функции показа bool Tag(const Context *context,const TagInfo *tag); }; //+------------------------------------------------------------------+
2. Реализуйте этот класс в файле PageNumberThree.cpp. По аналогии с заголовочным файлом, для быстроты скопируйте содержимое файла исходного кода первой страницы PageNumberOne.cpp в новый файл PageNumberThree.cpp и отредактируйте его следующим образом (изменения выделены желтым, ненужные куски кода удалены):
//+------------------------------------------------------------------+ //| TeamWox | //| Copyright © 2006-2008, MetaQuotes Software Corp. | //| https://www.metaquotes.net | //+------------------------------------------------------------------+ #include "StdAfx.h" #include "PageNumberThree.h" //+------------------------------------------------------------------+ //| Конструктор | //+------------------------------------------------------------------+ CPageNumberThree::CPageNumberThree() : m_server(NULL) { } //+------------------------------------------------------------------+ //| Деструктор | //+------------------------------------------------------------------+ CPageNumberThree::~CPageNumberThree() { m_server=NULL; } //+------------------------------------------------------------------+ //| Обработка запроса | //+------------------------------------------------------------------+ TWRESULT CPageNumberThree::Process(const Context *context,IServer *server,const wchar_t *path) { //--- проверки if(context==NULL || path==NULL) ReturnError(RES_E_INVALID_ARGS); if(context->request==NULL) ReturnError(RES_E_INVALID_CONTEXT); //--- получаем сервер if(server==NULL) ReturnError(RES_E_FAIL); //--- m_server=server; //--- отображаем страницу context->response->Write(L"Simple Text"); return(RES_S_OK); } //+------------------------------------------------------------------+ //| Обработка тэга | //+------------------------------------------------------------------+ bool CPageNumberThree::Tag(const Context *context,const TagInfo *tag) { //--- проверки if(context==NULL || tag==NULL || m_server==NULL) return(false); if(context->request==NULL || context->user==NULL) return(false); //--- return(false); } //+------------------------------------------------------------------+
Страница готова, но пока она никак не связана с модулем.
Новое правило перенаправления запросов
Чтобы обратиться к новой странице, нам потребуется добавить новое правило перенаправления запросов. В архитектуре MVC запросы принимает контроллер, в TeamWox его роль играет модуль. В соответствующем методе модуля добавим правило перенаправления запроса /helloworld/number_three на обработку страницы CPageNumberThree.
1. Откройте файл исходного кода модуля HelloWorldModule.cpp и внесите в него следующие изменения (выделены желтым):
//+------------------------------------------------------------------+ //| Роутинг по URL | //+------------------------------------------------------------------+ TWRESULT CHelloWorldModule::ProcessPage(const Context *context, IServer *server, const wchar_t *path) { if(context==NULL || path==NULL) ReturnError(RES_E_INVALID_ARGS); //--- if(PathCompare(L"index",path)) return(CPageIndex().Process(context,m_server,path)); if(PathCompare(L"number_one",path)) return(CPageNumberOne().Process(context,m_server,path)); if(PathCompare(L"number_two",path)) return(CPageNumberTwo().Process(context,m_server,path,&m_manager)); if(PathCompare(L"number_three",path)) return(CPageNumberThree().Process(context,m_server,path)); //--- по умолчанию return(CPageIndex().Process(context,m_server,path));
2. Добавьте определение класса CPageNumberThree в команды препроцессора:
#include "stdafx.h" #include "HelloWorldModule.h" #include "Pages\PageIndex.h" #include "Pages\PageNumberOne.h" #include "Pages\PageNumberTwo.h" #include "Pages\PageNumberThree.h"
Проверка отображения новой страницы
Теперь нам нужно проверить, что созданная страница доступна по HTTP-запросу. Предварительно убедитесь, что ваша среда разработки должным образом настроена.
1. Скомпилируйте проект, запустите сервер TeamWox и откройте главную страницу модуля Hello World.
2. В адресной строке браузера введите https://<ваш_сайт_teamwox>/helloworld/number_three.

Добавление ссылки на страницу в меню навигации модуля
Разумеется, запрашивать таким способом страницы не эффективно, поэтому мы добавим ссылку на страницу Page 3 в меню навигации модуля Hello World.
1. В текстовом редакторе откройте шаблон главной страницы модуля — файл <папка_установки_TeamWox>\modules\helloworld\templates\index.tpl и добавьте в него ссылку на страницу Page 3.
//+----------------------------------------------+
//| Шапка страницы |
//+----------------------------------------------+
var header = TeamWox.Control("PageHeader","#41633C")
.Help("/helloworld/index")
.Search(65536)
.Command("<lng:MENU_HELLOWORLD_NUMBER1>","/helloworld/number_one", "<lng:MENU_HELLOWORLD_NUMBER1>")
.Command("<lng:MENU_HELLOWORLD_NUMBER2>","/helloworld/number_two", "<lng:MENU_HELLOWORLD_NUMBER2>");
.Command("<lng:MENU_HELLOWORLD_NUMBER3>","/helloworld/number_three","<lng:MENU_HELLOWORLD_NUMBER3>");
2. Сохраните файл шаблон и в окне браузера откройте главную страницу модуля Hello World. Справа от двух существующих ссылок на страницы появилась новая.

3. Перейдите на новую страницу. Убедитесь, что в открывшемся фрейме отображается текст Simple Text.

4. Вернитесь на главную страницу модуля, используя средства навигации браузера.
Добавление переводов
Текст ссылки helloworld/number_three пока соответствует ключу MENU_HELLOWORLD_NUMBER3, так как сервер TeamWox не может найти соответствующий этому ключу перевод. Добавим его в языковой файл модуля.
1. В папке <папка_установки_TeamWox>\modules\helloworld\ откройте файл helloworld.lng в любом текстовом редакторе, добавьте ключ MENU_HELLOWORLD_NUMBER3 и переводы для всех поддерживаемых в модуле языков.

2. Сохраните изменения и перезапустите сервер TeamWox. Теперь название новой страницы берется из языкового файла helloworld.lng. Вы можете также проверить перевод на русский, изменив настройки языка в своем профиле.

Шаблоны
В описанном выше примере текст, выводимый на страницу, брался непосредственно из исходного кода. При таком подходе любое изменение представления (способ представления данных, оформления и т.д) потребует полной перекомпиляции модуля.
Чтобы уменьшить трудозатраты при изменении верстки страницы, следует выделить оформление страницы в шаблон. При таком подходе в исходном коде страницы будет указываться, какие данные должны быть представлены на страницы, а способ их оформления и порядок вывода будет определен в шаблоне.
Шаблоны страниц TeamWox — это специальные текстовые файлы, которые используются при выводе данных в окне браузера. Задача шаблонов — отделение программного кода, который отображает конкретные данные, от их оформления. Шаблон является своего рода посредником между данными страниц модуля и их отображением в браузере.
Отображение страницы с помощью шаблона
Итак, давайте изменим нашу страницу так, чтобы текст на ней выводился с помощью шаблона.
1. В папке <папка_установки_TeamWox>\modules\helloworld\templates\ создайте текстовый файл number3.tpl. Этот файл будет шаблоном для отображения страницы Page 3.
2. В текстовом редакторе добавьте в этот шаблон простейший HTML код.
<html> <body> Simple Text </body> </html>
3. Добавьте шаблон number3.tpl в проект HelloWorld.vcproj. Для этого в Visual Studio разверните папку Resource Files\templates и из контекстного меню выберите Add Existing Item.
4. Далее откройте папку <папка_установки_TeamWox>\modules\helloworld\templates\, выберите только что созданный нами файл number3.tpl и нажмите Add. Теперь вы можете изменять шаблоны непосредственно в среде Visual Studio.
Теперь нам нужно перенаправить вывод данных страницы на шаблон number3.tpl. Для этого откройте исходный код страницы PageNumberThree.cpp и измените следующий блок кода (изменения выделены желтым):
//+------------------------------------------------------------------+ //| Обработка запроса | //+------------------------------------------------------------------+ TWRESULT CPageReference::Process(const Context *context,IServer *server,const wchar_t *path) { //--- проверки if(context==NULL || path==NULL) ReturnError(RES_E_INVALID_ARGS); if(context->request==NULL) ReturnError(RES_E_INVALID_CONTEXT); //--- получаем сервер if(server==NULL) ReturnError(RES_E_FAIL); //--- m_server=server; //--- отображаем страницу return(server->PageProcess(context, L"templates\\number3.tpl", this, TW_PAGEPROCESS_NOCACHE)); }
6. Скомпилируйте модуль и запустите сервер TeamWox. В результате, на странице Page 3 мы должны получить тот же текст Simple Text, но теперь он отображается с помощью шаблона.
7. Важным преимуществом шаблонов является то, что для их изменения (с определенными ограничениями) не нужно заново компилировать модуль. Чтобы проиллюстрировать это, в текстовом редакторе откройте файл number3.tpl и измените в нем текст Simple Text — например, на Simple Text Changed (да!, для форматирования можно использовать HTML-теги). После этого просто обновите страницу в браузере.

Заключение
Итак, вы узнали как устроена архитектура модулей TeamWox, как в модули добавляются новые страницы, а также познакомились с мощным средством вывода данных — шаблонами страниц. В дальнейшем мы планируем более детально рассмотреть устройство шаблонов.
- Как добавить готовый модуль в TeamWox
- Как добавить страницу в модуль TeamWox
- Построение пользовательского интерфейса
- Взаимодействие с СУБД
- Создание пользовательских отчетов
- Файловое хранилище - Часть 1
- Файловое хранилище - Часть 2
- Настройка окружения пользовательских модулей - Часть 1
- Настройка окружения пользовательских модулей - Часть 2
- Поиск и фильтрация - Часть 1
- Поиск и фильтрация - Часть 2
- Настройка "Онлайн-консультанта" на вашем сайте
- Как создать дополнительный языковой пакет для TeamWox
2010.08.10