Подсказки по Yii. Глава девятнадцатая.
-
Использование CHtml::listData.
Имеется запрос:
- $ids = array(18, 19, 20, 21);
- $sql = 'SELECT id_object, COUNT(id) as count FROM {{images}} WHERE id_object IN ('.implode(',', $ids).') GROUP BY id_object';
- $res = Yii::app()->db->createCommand($sql)->queryAll();
Результатом выполнения запроса будет следующий массив:
- Array
- (
- [0] => Array
- (
- [id_object] => 18
- [count] => 3
- )
-
- [1] => Array
- (
- [id_object] => 19
- [count] => 3
- )
-
- [2] => Array
- (
- [id_object] => 20
- [count] => 4
- )
-
- [3] => Array
- (
- [id_object] => 21
- [count] => 2
- )
- )
Задача: вернуть массив, в котором ключами будут id_object, а значениями ключей будет count.
Конечно, можно использовать циклы foreach / for / while ...
Однако, фреймворк Yii тем и хорош, что в нём много "магических" методов.
Всё, что потребуется - это вставить строку кода:
- return CHtml::listData($res, 'id_object', 'count');
В результате получится массив, который нам нужен:
- Array
- (
- [18] => 3
- [19] => 3
- [20] => 4
- [21] => 2
- )
-
Вывод ошибок валидации в блоке, который можно закрыть.
Практическое применение: мобильная версия сайта/адаптивный дизайн, где видимая область экрана ограничена. Поэтому пользователь, прочитав описание ошибок, может скрыть их. Тем самым опять вернуть обзор "полезной" части сайта.
Если в проекте используется Yii BootStrap, то вместо:
- <?php echo $form->errorSummary($model); ?>
пропишем:
- <?php
- if (CHtml::errorSummary($model)) {
- Yii::app()->user->setFlash('error', CHtml::errorSummary($model));
- $this->widget('bootstrap.widgets.TbAlert');
- }
- ?>
Это позволит по "крестику" закрывать список ошибок.
Если в проекте Yii BootStrap не используется - ничего страшного, сами добавим нужный функционал:
Вместо:
- <?php echo $form->errorSummary($model); ?>
пропишем:
- <?php if (CHtml::errorSummary($model)) :?>
- <div class="error-block">
- <a class="close" href="javascript:void(0);">×</a>
-
- <?php echo CHtml::errorSummary($model);?>
- </div>
-
- <?php
- $css=<<<EOT
- .error-block, .error-block .errorSummary { background-color: #DE6D6B !important; color: #FFFFFF; }
- .error-block .close { float: right; font-size: 22px; position: relative; right: 9px; text-decoration: none; top: 1px;}
- EOT;
- Yii::app()->clientScript->registerCss('inline.css', $css);
-
- Yii::app()->clientScript->registerScript('close-action', "
- $('.error-block .close').click( function(){ $(this).parent().fadeOut(500); });
- ", CClientScript::POS_END);
- ?>
- <?php endif;?>
-
CListView. Передача дополнительных параметров в представление.
В коде есть вызов CListView:
- $this->widget('zii.widgets.CListView', array(
- 'dataProvider' => $dataProvider,
- 'itemView' => '_view',
- 'itemsTagName' => 'ol',
- 'itemsCssClass' => 'advertising-blocks',
- 'sortableAttributes' => array(
- 'position',
- 'type',
- 'active',
- ),
- ));
Необходимо в представлении _view.php, кроме объекта $data, знать значение текста в переменной $text.
Для этого добавим viewData:
- 'viewData' => array('text' => 'Здесь некий текст'),
Вызов примет вид:
- $this->widget('zii.widgets.CListView', array(
- 'dataProvider' => $dataProvider,
- 'viewData' => array('text' => 'Здесь некий текст'),
- 'itemView' => '_view',
- 'itemsTagName' => 'ol',
- 'itemsCssClass' => 'advertising-blocks',
- 'sortableAttributes' => array(
- 'position',
- 'type',
- 'active',
- ),
- ));
Теперь, в представлении можно отобразить значение переменной $text.
Также, можно воспользоваться "клипом". Для этого в контроллере пропишем:
- $this->beginClip('testClip');
- echo 'Здесь некий текст';
- $this->endClip();
А в представлении _view.php добавим код:
- <?php
- if (isset($this->clips['testClip']) && !empty($this->clips['testClip'])) {
- echo $this->clips['testClip'];
- }
- ?>
-
CViewAction. Статические страницы в Yii.
Для примера возьмём скрипт для сайта-визитки Open Business Card.
Создадим в директории protected/views папку staticpages.
В эту папку добавим два файла: staticpage1.php и staticpage2.php.
Содержимое файла staticpage1.php:
- <p>Это пример статической страницы #1.</p>
- <p>Такая страница редактируется в текстовом редакторе.</p>
Содержимое файла staticpage2.php:
- <p>Это пример статической страницы #2.</p>
В файле protected/controllers/SiteController.php заменим код:
- public function actions() {
- return array(
-
- 'captcha' => array(
- 'class' => 'MathCCaptchaAction',
- 'backColor' => 0xFFFFFF,
- ),
-
-
- 'page' => array(
- 'class' => 'CViewAction',
- ),
- );
- }
на:
- public function actions() {
- return array(
-
- 'captcha' => array(
- 'class' => 'MathCCaptchaAction',
- 'backColor' => 0xFFFFFF,
- ),
-
-
- 'staticpage' => array(
- 'class' => 'CViewAction',
- 'basePath' => 'application.views.staticpages', # директория, в которой находятся статические страницы.
- 'renderAsText' => true, # в противном случае будет обрабатываться PHP-код, если он есть на странице.
- 'defaultView' => 'staticpage1', # страница по-умолчанию
- 'layout' => '//layouts/user', # макет для статических страниц. Если указано null, то страница будет без макета
- ),
- );
- }
Теперь можно вызывать статические страницы таким образом:
http://site_domain/site/staticpage/view/staticpage1 и http://site_domain/site/staticpage/view/staticpage2
Ссылки не совсем красивые. Исправим это.
В файл protected/config/main.php добавим правило (секция urlManager):
- 'statpage/<view:(staticpage1|staticpage2)>' => array('site/staticpage'),
Теперь статические страницы вызываются так:
http://site_domain/statpage/staticpage1 и http://site_domain/statpage/staticpage2