+7 495 008 8452 пн.-пт. 10:00 – 17:00
Если у вас возникли какие либо вопросы которые вы не смогли решить по нашим публикациям самостоятельно,
то ждем ваше обращение в нашей службе тех поддержки.


Добавляем свой элемент в Живую Ленту

В этой статье рассмотрим как добавить в ЖЛ новый элемент. Рассмотрим на примере новостей (или любых других элементов ИБ).


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

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

0. Придумаем название для ENTITY_TYPE и EVENT_ID.
ENTITY_TYPE - это тип ваших событий. Например, MYNEWS (макс.длина 50 символов, только буквы и цифры. рекомендуется со своим префиксом, чтобы не случилось конфликта)
EVENT_ID - ID события, но тоже константа. Пусть будет news.

Все методы будут в классе CSonetLogHandlers, ниже перечислю его методы.

1. Для начала заведем три обработчика событий:

AddEventHandler('socialnetwork', 'OnFillSocNetLogEvents', array('CSonetLogHandlers', 'OnFillSocNetLogEvents'));
AddEventHandler('socialnetwork', 'OnFillSocNetFeaturesList', array('CSonetLogHandlers', 'OnFillSocNetFeaturesList'));
AddEventHandler('socialnetwork', 'OnFillSocNetAllowedSubscribeEntityTypes', array('CSonetLogHandlers',  
'OnFillSocNetAllowedSubscribeEntityTypes'));
 


2. OnFillSocNetLogEvents. Собственно обработчик

public static function OnFillSocNetLogEvents(&$arSocNetLogEvents)
{
   $arSocNetLogEvents['news'] = array(
      'ENTITIES'   =>   array(
         'MYNEWS' => array(
            'TITLE'          => 'Новости',
            'TITLE_SETTINGS'   => 'Все новости',
            'TITLE_SETTINGS_1'   => 'Уведомления о новостях',
            'TITLE_SETTINGS_2'   => 'Уведомления о новостях',
         ),
      ),
      'CLASS_FORMAT'   => 'CSonetLogHandlers',
      'METHOD_FORMAT'   => 'FormatEventNews'
   );
}

Как вы можете видеть - в ключах присутствуют сущности из п.0. От комментариев воздержусь. Языковые значения предназначены для вывода в разных местах ЖЛ. По логике их можете изменить.

3. OnFillSocNetFeaturesList.

public static function OnFillSocNetFeaturesList(&$arSocNetFeaturesSettings)
{
   $arSocNetFeaturesSettings['news']['subscribe_events']['news']['ENTITIES']['MYNEWS'] = array();
} 


И опять тут видим сущности из п.0. Просто примите как должное данный массив :)  

4. OnFillSocNetAllowedSubscribeEntityTypes.

public static function OnFillSocNetAllowedSubscribeEntityTypes(&$arSocNetAllowedSubscribeEntityTypes)
{
   $arSocNetAllowedSubscribeEntityTypes[] = 'MYNEWS';

   global $arSocNetAllowedSubscribeEntityTypesDesc;
   $arSocNetAllowedSubscribeEntityTypesDesc['MYNEWS'] = array(
      'TITLE_LIST'      => 'Новости',
      'CLASS_DESC_GET'   => 'CSonetLogHandlers',
      'METHOD_DESC_GET'   => 'GetIBlockByID',
      'CLASS_DESC_SHOW'   => 'CSonetLogHandlers',
      'METHOD_DESC_SHOW'   => 'ShowEntityLink',
   );
}


Аналогично. Сущность MYNEWS. Опять принимаем как должное.

5. Страшный и ужасный метод, который отвечает как за показ новости в ЖЛ, так и за ее отправку по e-mail или ЛС (если есть такие указания подписчика). Также здесь собираются поля тултипа всплывающего и прочее. Если есть желание разобраться, просто поэкспериментируете параметрами.

public static function FormatEventNews($arFields, $arParams, $bMail = false)
{
   $arEventParams = unserialize(strlen($arFields['~PARAMS']) > 0 ? $arFields['~PARAMS'] : $arFields['PARAMS']);

   $arResult = array('EVENT' => $arFields, 'ENTITY' => array(), 'URL' => '');
   $arResult['ENTITY']['TYPE_MAIL'] = ' разделе';
   if (!$bMail)
   {
      $arResult['ENTITY']['FORMATTED'] = array();
      $arResult['ENTITY']['FORMATTED']['URL'] = $arEventParams['ENTITY_URL'];
      $arResult['ENTITY']['FORMATTED']['NAME'] = $arEventParams['ENTITY_NAME'];
   }
   else
      $arResult['ENTITY']['FORMATTED'] = 'Новости';

   if (!$bMail)
      $title = 'Добавлена новость <a href="'.$arFields['URL'].'">'.$arFields['TITLE'].'</a>';
   else
      $title = 'Добавлена новость: ' . $arFields['TITLE'];

   $arResult['EVENT_FORMATTED'] = array(
                        'TITLE'         => $title,
                        'MESSAGE'      => ($bMail ? CSocNetTextParser::killAllTags($arFields['MESSAGE']) : $arFields['MESSAGE']),
                        'IS_IMPORTANT'   => false
                     );
   if (!$bMail)
   {
      $arFieldsTooltip = array(
         'ID'         => $arFields['USER_ID'],
         'NAME'         => $arFields['~CREATED_BY_NAME'],
         'LAST_NAME'      => $arFields['~CREATED_BY_LAST_NAME'],
         'SECOND_NAME'   => $arFields['~CREATED_BY_SECOND_NAME'],
         'LOGIN'         => $arFields['~CREATED_BY_LOGIN'],
      );
      $arResult['CREATED_BY']['TOOLTIP_FIELDS'] = CSocNetLog::FormatEvent_FillTooltip($arFieldsTooltip, $arParams);
      $arResult['AVATAR_SRC'] = CSocNetLog::FormatEvent_CreateAvatar($arFields, $arParams, 'CREATED_BY');

      $arResult['EVENT_FORMATTED']['IS_MESSAGE_SHORT'] = CSocNetLog::FormatEvent_IsMessageShort($arFields['MESSAGE']);
      $arResult['EVENT_FORMATTED']['URL'] = $arFields['URL'];
   }
   else
      $arResult['EVENT_FORMATTED']['URL'] = 'http://' . $_SERVER['SERVER_NAME'] . $arFields['URL'];

   return $arResult;
} 


Пару слов о 'IS_IMPORTANT' => false у $arResult['EVENT_FORMATTED']. Если его поставить в true, то новость выделится такой красивой рамочкой:



Если оставить в false, будет типичная запись, с автором и прочими атрибутами.

6. В п.4 описываются некие методы. Они отвечают за получение информации об инфоблоке и выводе его в подписке (ссылки слева в блоках "статьи" и "форумы";):




Это GetIBlockByID и ShowEntityLink.

public static function GetIBlockByID($ID)
{
   if (CModule::IncludeModule('iblock'))
      if ($arInfo = CIBlock::GetByID($ID)->GetNext())
         return array('NAME_FORMATTED' => $arInfo['NAME'], 'URL' => $arInfo['LIST_PAGE_URL']);
}


public static function ShowEntityLink($arEntityDesc, $strEntityURL, $arParams)
{
   return '<a href="'.$arEntityDesc['URL'].'">'.$arEntityDesc['NAME_FORMATTED'].'</a>';
} 


Ну все. Обработчики все написаны. Осталось добавить запись в лог.

7. За это отвечает вот такая относительно не страшная функция:

function AddToLog($elID, $entityType)
{
   if (CModule::IncludeModule('socialnetwork') && CModule::IncludeModule('iblock'))
   {
         $arElfields = CIBlockElement::GetByID($elID)->GetNext(true, false);
         $arIB = CIBlock::GetByID($arElfields['IBLOCK_ID'])->GetNext(true, false);
         $site_id = $arIB['LID'];

         $arSoFields = Array(
               'SITE_ID'         => $site_id,
               'ENTITY_TYPE'       => $entityType,
               'ENTITY_ID'       => $arElfields['IBLOCK_ID'],
               'EVENT_ID'          => $arIB['IBLOCK_TYPE_ID'],
               'USER_ID'          => $arElfields['CREATED_BY'],
               '=LOG_DATE'       => (
                                    strlen($arElfields['ACTIVE_FROM']) > 0
                                    ?
                                       (
                                          MakeTimeStamp($arElfields['ACTIVE_FROM'], CSite::GetDateFormat('FULL', $site_id)) > time()
                                          ?
                                             $GLOBALS['DB']->CharToDateFunction($arElfields['ACTIVE_FROM'], 'FULL', $site_id)
                                          :
                                             $GLOBALS['DB']->CurrentTimeFunction()
                                       )
                                    :
                                       $GLOBALS['DB']->CurrentTimeFunction()
                                 ),
               'TITLE_TEMPLATE'    => 'Новость: #TITLE#',
               'TITLE'          => $arElfields['NAME'],
               'MESSAGE'          => $arElfields['PREVIEW_TEXT'],
               'TEXT_MESSAGE'       => '',
               'URL'            => $arElfields['DETAIL_PAGE_URL'],
               'MODULE_ID'       => 'iblock',
               'CALLBACK_FUNC'    => false,
               'TMP_ID'          => false,
               'PARAMS'         => serialize(array(
                                 'ENTITY_NAME'      => $arIB['NAME'],
                                 'ENTITY_URL'      => $arIB['LIST_PAGE_URL']
                              ))
            );
      $logID = CSocNetLog::Add($arSoFields, false);
      if (intval($logID) > 0)
      {
         CSocNetLog::Update($logID, array('TMP_ID' => $logID));
         CSocNetLog::SendEvent($logID, 'SONET_NEW_EVENT');
      }
   }
}


Функции передается ID элемента ИБ и тип события (MYNEWS).

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

Все.

Назад в раздел

Подписаться на новые материалы раздела:












CAPTCHA