Как стать автором
Обновить

Комментарии 14

Прочитав, у меня сложилось впечатление что автор поставил перед собой задачу «Как-бы зделать себе жизнь по сложнее?» и по этому решил заняться отечественным велосипедостроением.

Сорри но не могу не прокомментировать:
Чем не устраивает коровский блок переключения языков? Если блок не устраивает тем что переключатель нужно позиционировать в нестандартном регионе, так есть другие альтернативы типа Panels и Panels everywhere. Ну или если искать самое простое решение для задачи «впихнуть невпихуемое куда-то в контент» ), что-бы расположить ссылки где-то в node.tpl.php (сложилось впечатление что ради этого все затеивалось), то в node.tpl.php никто не запрещает использовать следующий код:

<?php if (function_exists('locale_block')):
$locale_block = locale_block('view');
echo $locale_block['content'];
endif; ?>


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

Если-же речь идет о функционале для отоброжения спец. страницы в случае если нод не переведен, то это можно решить написав модуль который имплементирует hook_translation_link_alter()

Кроме того хочу заметить что для того что-бы не иметь проблем с алиасами страниц в друпале, не стоит просто собирать ссылки таким методом:

$output = '<li><a href="/ua/'.$path[uk].$path_tax.'">ua</a></li>
<li><a href="/'.$path[ru].$path_tax.'">ru</a></li>
<li><a href="/en/'.$path[en].$path_tax.'">eng</a></li>';


В друпале для этого есть функции url() и l(), которые для того и предназначены что-бы можно-было не волноваться об алиасах.
После вашего комментария и добавить то нечего особо )
Спасибо=)

Но я вот вспомнил что добавить:
Что-бы не парится с удалением кэша (бегая по разным подстраницам админки) ставим модуль admin_menu которое дает отдельную подменюшку для чистки кэшей. Можно одним кликом почистить нужный кэш ну или сразу все. Кроме того значитильно ускоряет перемещение по админке. ;)
Модуль admin_menu я юзаю уже не один год. Но мы не все.
Статья писалась с учетом прочтения ее непосвященными.
Коммент достоин внимания.

Использование кода:
<?php if (function_exists('locale_block')):
 $locale_block = locale_block('view');
 echo $locale_block['content'];
endif; ?>

однозначно решает задачу облегчить себе жизнь, но не решает поставленной в статье задачи.

Сравниваем код на выходе:

Результат решения описанного в посте:
<ul class=" img_link_list lang_li">
    <li><a href="/ua/my-alias">ua</a></li>
    <li><a href="/my-alias">ru</a></li>
    <li><a href="/en/my-alias">eng</a></li>
</ul>


и результат вывода locale_block:
<ul>
    <li class="en first"><a href="/en/node/35" class="language-link">English</a></li>
    <li class="ru active"><a href="/my-alias" class="language-link active">Русский</a></li>
    <li class="uk last"><a href="/ua/node/36" class="language-link">Українська</a></li>
</ul>


Вариант "*/node/хх" большинство однозначно не устроит, меня точно.

А если нужно вывести хотя-бы так (или иначе, зависимо от стоящей задачи):
<ul class=" img_link_list lang_li">
    <li><a href="/ua/my-alias"><img src="ua.jpg" /></a></li>
    <li><a href="/my-alias"><img src="ru.jpg" /></a></li>
    <li><a href="/en/my-alias"><img src="en.jpg" /></a></li>
</ul>


В последнем варианте напрашивается установка модуля «Language icons», только он тоже не решает задач тогда кода нужно гибко темизировать вывод.
Можно использовать и «hook_translation_link_alter()» изменив атрибуты линка но только не сам линк.

А вот использование довольно грузных модулей как Panels и Panels everywhere, а соответственно и CTools для для вывода трех линков считаю совершенно лишним, это явно не облегчит жизнь.

УПС: Не считаю свое решение идеальным. Для решения любой задачи есть как минимум несколько решений. Я остановился на этом поделился с теми кто имеет похожие задачи и сумеет использовать для решение своих.
Используя hook_translation_link_alter() можно менять полностью массив УРЛов до того как те пойдут в обработку (включая саму ссылку если необходимо).
Если хочется флажки, то есть вариант и получше Language icons. Например: Consistent Language Interface. Несмотря на то-что он больше не ментэйнится, он работает довольно хороше.

Ваш пример созданных ссылок немного странноват, так-как locale_block('view'); отдает все ссылки прогнанные через theme('links'); где опять-же используется l(); которая автоматически подставляет алиасы если такие имеются. Судя по вашему примеру у вас на ua и en переводы нода не заведены алиасы, иначе-бы ссылки были уже с ними.
Проверил.
Заведены.
Решение через locale_block мне тоже очень понравилось и однозначно буду его использовать (за вариант отдельная благодарность).
Но в моем варианте под тот проект, для которого это писалось, мой вариант работает корректнее (пробовал разные).
Сама тема мало освещена в сети, так что уверен наша дискусия окажется полезной не одному человеку.
Благодарочка, что не прошли мимо!!!
Да уж :)

Во-первых, код не учитывает language negotiation выбранную в админке, не будет работать с выключенным mod_rewrite или если сайт перенесут в подпапку.

Во-вторых, модуль locale позволяет изменить ссылки:
drupal_alter('language_switch_links', $result, $type, $path);

И в-третьих, в теме можно перекрыть функцию темизации:
$block['content'] = theme('links__locale_block', $variables);

А как, вывести блок в самой ноде вверху уже написали, хотя лучшим решением будет добавить новую переменную в hook_preprocess_node.
Комментарий выше для 7-ой версии.

В 6-ой версии нельзя перекрыть специфическую для locale_block версию theme('links'), и альтер немного другой:
drupal_alter('translation_link', $links, $path);

А так всё то же самое.
Перекрывается в теме theme_* функцией как минимум
В 6-ом можно перекрыть только theme_links, которая используется ещё в многих местах, поэтому на мой взгляд нежелательно.

В 7-ом же добавили возможность перекрыть вывод для каждого частного случая через механизм theme function suggestions не трогая «главную» theme_links вообще. Больше на drupal.org
Я решил эту задачу так: выводим стандартный блок переключения языков, скрываем его через CSS, добавляем jquery скрипт:
(function($) {
  if (jQuery("body").hasClass("i18n-ru")) {  // если русский
    // удаляем ссылку у текущего языка
    html_ru = jQuery('#ru_lang a').html();
    jQuery('#ru_lang').html(html_ru);
    // копируем ссылку из стандартного блока языков
    link_en = jQuery('#block-locale-language ul li.en a').attr('href');
    jQuery('#en_lang a').attr('href', link_en);
  } else { // если английский
    html_en = jQuery('#en_lang a').html();
    jQuery('#en_lang').html(html_en);
    link_ru = jQuery('#block-locale-language ul li.ru a').attr('href');
    jQuery('#ru_lang a').attr('href', link_ru);
  }
    })(jQuery);

Довольно просто и функционально, оформление списка языков таким образом может быть любым.
Как по мне, то вариант с jQuery возможно и стоит попробовать.
Но меня он в корне не устроил бы.

Причины:

1. Браузеры с отключенным javascript
2. Googlebot не будет разбирать jQuery, а вот «display: none;» ему хорошо знаком и не любим

Это лично мое мнение.
1. при отключенном javascript браузер будет переходить по изначальной ссылке на главную страницу языка (site.ru/en/).
2. Соответственно и Googlebot будет индексировать англоязычный раздел сайта нормально.
Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Изменить настройки темы

Истории