Мы подключаем файл myquestions.html.phpс помощью require_once(JApplicationHelper::getPath('html')) и папку tableбэкенда с помощью JTable::addIncludePath(). Обратите внимание, что мы обращаемся к классам таблиц бэкенда, хотя пишем фронтенд компонента.
Переключатель switch обрабатывает пока только значение задачи по умолчанию, вызывая функцию для получения списка категорий.
Теперь добавим класс HTML_questions для фронтенда. Создайте файл /components/com_myquestions/myquestions.html.php:
<?php class HTML_questions { function showCategories($rows, $option) { ?> <p><a href='index.php?option=<?=$option?>&task=showlist'><?= JText::_('COM_MYQUESTIONS_ALL_QUESTIONS')?></a></p> <table> <?php foreach($rows as $row) { $link = 'index.php?option='.$option.'&id_cat='.$row->id.'&task=showlist'; echo '<tr><td><p><a href="' . $link . '">'.$row->name .'</a></td><td>'.$row->desc.'</td></tr>'; } ?> </table> <?php } } ?>
Класс HTML_questions будет содержать все функции вывода во фронтенде. Функция showCategories() принимает в качестве параметров массив записей таблицы базы данных и название текущего компонента. В цикле осуществляется обход этого массива и каждая запись выводится на экран.
Создайте файл /language/ru-RU/ru-RU.com_myquestions.iniи скопируйте в него строку:
COM_MYQUESTIONS_ALL_QUESTIONS="Все вопросы"
Теперь на странице компонента myquestions во фронтенде по умолчанию отображается список категорий (рис. 4.9).
![Разрботка расширений для CMS Joomla _37.jpg](https://litlife.club/books/145279/read/images/_37.jpg)
(есть увеличенное изображение)
Рис. 4.9. Вывод списка категорий во фронтенде
Просмотр списка вопросов
Измените код конструкции switch в файле myquestions.php, добавив обработку задачи showlist:
case 'showlist': showQuestions($option); break;
Добавьте в этот же файл функцию showQuestions():
function showQuestions($option) { $db =& JFactory::getDbo(); $query = "SELECT q.id,q.name,q.date,q.question,q.city,q.email,q.answer,q.id_cat,c.name AS cname ". "FROM #__myquestions q, #__myquestions_categories c ". "WHERE q.id_cat=c.id AND q.answer <> '' AND (q.published = 1 OR (q.expiration_date <> '0000-00-00 00:00:00' AND q.expiration_date > NOW()))"; $id_cat = JRequest::getVar('id_cat', '0'); if ($id_cat != 0) $query .= " AND q.id_cat = $id_cat"; $db->setQuery($query); $rows = $db->loadObjectlist(); if ($db->getErrorNum()) { echo $db->stderr(); return false; } if ($id_cat != 0) { $query = "SELECT name FROM #__myquestions_categories WHERE id=$id_cat"; $db->setQuery($query); if ($db->getErrorNum()) { echo $db->stderr(); return false; } $name_cat = $db->loadResult(); } else $name_cat = ''; HTML_questions::showQuestions($rows, $option, $name_cat); }
Длинный SQL-запрос требует пояснения. Как вы помните, при описании функциональности нашего компонента упоминалось, что отображаться на сайте будут вопросы, удовлетворяющие следующим условиям:
есть ответ;
либо вопрос не помечен как скрытый, либо дата снятия вопроса с публикации указана и больше текущей даты.
Данный запрос выбирает вопросы, которые соответствуют этим условиям.
Проверяется значение переменной $id_cat (id категории), и если категория задана, то из базы выбираются только вопросы, отнесенные к этой категории. Затем извлекается название категории для отображения над списком вопросов. Если же категория не задана, то выбираются вопросы из всех категорий.
Добавьте в класс HTML_questions в файле myquestions.html.phpследующую функцию:
function showQuestions($rows, $option, $name_cat) { if ($name_cat !== '') echo "<h1>$name_cat</h1>"; foreach($rows as $row) { $link = 'index.php?option='.$option.'&id='.$row->id.'&task=showquestion'; $link_cat = 'index.php?option='.$option.'&id_cat='.$row->id_cat.'&task=showlist'; ?> <table width="100%"> <tr> <td><i><?=$row->name?></i></td> <td><i><u><?=$row->email?></u></i></td> <td><i><?=JHTML::_('date', $row->date, JText::_('DATE_FORMAT_LC3'))?></i></td> <td><i><?=$row->city?></i></td> </tr> <tr> <td colspan="4"><a href="<?=$link_cat?>"><?=$row->cname?></a></td> </tr> <tr> <td colspan="4"><b><?=$row->question?></b></td> </tr> <tr> <td colspan="4"><?=$row->answer?></td> </tr> <tr> <td colspan="4"><a style="text-decoration: none;" title="<?=JText::_('COM_MYQUESTIONS_READMORE')?>" alt="<?=JText::_ ('COM_MYQUESTIONS_READMORE')?>" href="<?=$link?>">---></a></td> </tr> </table> <br/> <? } }
Данная функция выводит название категории, если оно задано, и затем проходит в цикле по всем записям, переданным ей. Для каждой записи выводится таблица с теми ее полями, которые были извлечены ранее.
Добавьте в файл language/ru-RU/ru-RU.com_myquestions.iniстроку:
COM_MYQUESTIONS_READMORE="Подробнее"
Для проверки работоспособности нового кода нажмите на ссылку " Все вопросы" во фронтенде нашего компонента. Результат должен быть приблизительно таким, как на рис. 4.10.
![Разрботка расширений для CMS Joomla _38.jpg](https://litlife.club/books/145279/read/images/_38.jpg)
(есть увеличенное изображение)
Рис. 4.10. Список вопросов во фронтенде
Вывод одного вопроса
Иногда может понадобиться вывести какой-либо один вопрос. Например, если пользователь захочет поделиться ссылкой на свой вопрос с кем-то другим.
Измените код конструкции switch в файле myquestions.php, добавив обработку задачи showquestion:
case 'showquestion': showQuestion($option); break;
Добавьте в этот же файл функцию showQuestion():
function showQuestion($option) { $id = JRequest::getVar('id', 0) ; $row = &JTable::getInstance ('question', 'Table'); $row->load($id); if ($row->answer == '' || ($row->published == 0 && ($row->expiration_date == '0000-00-00 00:00:00' || strtotime($row->expiration_date) <= time()))) JError::raiseError(404, JText::_(' COM_MYQUESTIONS_ERROR404')); $row_cat =& JTable::getInstance('Category','Table'); $row_cat->load($row->id_cat); HTML_questions::showQuestion($row, $option, $row_cat); }
В данном коде мы получаем id из запроса к серверу с помощью функции getVar(). Если значение id отсутствует или неприемлемо, будет использовано значение по умолчанию, переданное во втором параметре (ноль). Затем мы получаем экземпляр класса таблицы из бэкенда и загружаем запись таблицы базы данных, соответствующую идентификатору id.
Далее происходит проверка того, можно ли отображать в открытом доступе данный вопрос. Исходя из условий отображения вопроса на сайте, нетрудно заметить, что не должны отображаться на сайте вопросы, удовлетворяющие хотя бы одному из условий:
нет ответа;
вопрос помечен как скрытый и дата снятия вопроса с публикации не указана или меньше или равна текущей дате.
Если вопрос не должен отображаться, то используется функция raiseError() класса JError для вывода сообщения " 404 - Вопрос не найден". Такое же сообщение появится при попытке обращения к несуществующей записи.
Добавьте в файл language/ru-RU/ru-RU.com_myquestions.iniстроку: