Здравствуйте, умные люди.
И снова тема выделения текущих пунктов меню, которые создаются заново и не являются ни примари ни секондери, все еще не решена, или мне так кажется потому что я недостаточно долго рылся на этом форуме)).
так вот, как же всетаки классик прибавить?
даже на этом сайте выделение текущего пункта по-калечному организовано, вроде бы оно есть, но как только на внутреннюю страницу к примеру форума переходишь - классик удаляется...
использую nice menu, необходимо чтобы классик текущего пункта, не важно к ребенку списка, либо к самой ссылке добавлялся, причем чтобы сохранялась логика, т.е. если у пункта есть подпункты, и если подпункт на котором находишься является ребенком к основному пункту, то классик должен добавляться как к родительскому пункту, так и к пункту-ребенку, довольно логично, не находите? (:
решил пройтись по ссылкам примеров сайтов использующих найсменю и ужаснулся, там никто тупо не думает о пользователях и не подсвечивает пункты меню))) это жестяк какой-то.
Уважаемые, неужели это так сложно? нужно много программировать чтобы учесть все возможные варианты, или всетаки есть уже, хоть-какое-то более-менее вменяемое решение этой огромной проблемы?
не взыщите если мои возлияния верстальщика покажутся слишком наивными
Комментарии
a class="active" добавляется к активной ссылке по умолчанию, год назад делал, по-моему так... Нужно выделить активную ссылку в данный момент, я правильно понял?
Извините, igorek, но я специально уточнил, что использую модуль nice menu, и прежде чем задавать вопрос все перепроверил.
Также я прокомментировал свою осведомленность насчет того, что по крайней мере в меню построенном на основе секондери линкс класс, обозначающий активный пункт меню присваивается.
Никакого класса, обозначающего активный пункт меню, в созданном меню на основе модуля nice menu не добавляется ни к ребенку списка этого пункта, ни к ссылке, которая в этом эелементе списка находится.
Да Вы правильно поняли, мне нужно присвоить текущему элементу меню класс (в данном случае текущим я называю элемент меню которому соответствует адрес загруженной в браузере страницы).
Модуль menutrails, кажется, решает проблему
спасибо, qwaker, поставил модуль, ничего не изменилось(( настроек у модуля нет, тупо ставишь, активируешь и все... видимо с найсменю он не работает, и нужно что-то другое.. вот гадство, я уже и в темплейт пхп функцию запихнул для добавления к этому меню класса для первого и последнего пункта, все работает, и вот на этих активных пунктах кажется какой-то тупик...
может еще кто-нибудь что-нибудь посоветует?
ну у меня же работает, и именно nicemenu. класс для активного элемента меню active-trail.
да уж, видимо никто не знает универсального решения) странно, этож почти основы юзабилити, неужели в друпале для этого ничего путного нет?:)
вот гражданин видимо тоже разочаровался (: http://www.drupal.ru/node/32800
Проверил на 6-ке nice_menus 6.x-1.3
У меня всё работает...
Если все таки не работает, то вот безумная мысль:
Все это до выделенного жирным текста можно в общем то не читать
1) создать свою theme функцию lala_theme_nice_menu_build(поглядеть оригинальную функцию ), зарегестрировать ее
2) поглядеть функцию menu_get_active_trail (и menu_set_active_trail) и поглядеть функцию menu_get_active_title, которая ее использует, чтобы получить заголовок активной страницы из подсистемы меню drupal, там много чего еще оказывается лежит, в частности href текущей страницы. Написать свою
get_active_path. Не забыть, что в href свойстве может быть и alias вместо оригинального url-а. Обратить внимание, что сама функция возвращает как я понимаю целый набор пунктов от корня меню спускаясь до пункта меню, которому соответствует текущая открытая страница
3) в функции из пункта 1), отловить все пункты от корня до текущего активного пункта и проставить в них свойство active
-) к сожалению своих функций nice_menu_item для установки пользовательских классов модуль nice_item не имеет
X) Возможно active не проставляется из-за alias-ов. Например в меню будет именно alias на страницу, а menu_get_active_trail (у меня покрайне мере) возвращает истинный url, т.е. node/xxx, а не alias, соответственно класс active и не появляется, так как не было найдено соответствия. У меня правда еще хуже, у меня несколько alias-ов висит на один node/xxx, а пункт меню также надо было подсвечивать.
X+1) поглядев на функцию menu_get_active_title, могу еще добавить, что прямо как там делать не надо, так как там еще проверка на тип MENU_IS_LOCAL_TASK. Так как там просто заголовок нужен, а не идентификатор активного пункта меню.
X+2) что касается nice_menu я так понимаю это javascript menu без перезагрузки страницы, оно грузица целиком и потмо вы по нему ходите. Только вот в коде модуля я не нашел чего либо чтобы сразу устанавливало свойство активного пункта меню, проставляются только классы определяющие тип пункта меню, дочерний пункт без детей или с детьми. Вероятно пункт меню для открытой страницы открывается средствами самого javascript+jquery. Поэтому вариантов несколько:
1) отключен javascript
2) глючит код javascript для вашего броузера
3) вариант с alias-ом, т.е. javascript видет только alias страницы, а в пункте меню прописан исключительно истинный адрес node/xxx, соответственно javascript не находит пункта меню для страницы и его подсветки не проивзодится.
Правда кода на javascript подсвечивающего пункт меню открытой страницы я тоже что то не нашел.
Я смотрел код nice_menu версии 6.x-1.3
Модуль сам не подсвечивает пункт меню активной страницы и родительские пункты тоже. Т.е. задачка раздваивается, делать это на javascript, но на сайте без alias-ов или делать свою theme_nice_menu_build функцию, установив соответствующий класс, используя функцию menu_get_active_trail для поиска пункта активной страницы и всех ее родительских пунктов.
Что касается класса active, добавляется он функцией theme_menu_item_link
которая стандартная для drupal, так как она вызывается из nice_menu_build, чтобы создать ссылку. Точнее она вызывает внутри известную функцию l(), которая внутри как раз тоже анализирует _GET('q') и прописывает тот самый active, если ссылка в _GET('q') текущая страница. Посмотрите function l(
в coomin.inc и станет понятно откуда берется .active у ссылок. Но только надо отметить, что он у ссылки, а в nice_menu класс выставляется для ul элемента. Но если дописать какой нить jquery-css типа:
SelectItems{color:f00;}
$('ul:has(a.active)').addClass{SelectItems};
то будет подсвечиваться любой ul, который внутри имеет ссылку с классом active
В jquery не силен, не бить, но что-то типа этого, так как определить класс тольк через css не выйдет, там нет xml селекторов увы.
Есть вероятность что в вашей теме эта функция кем-то еще перебита, потому и не выставляется active.
Как только active будет выставлен, то можно подумать уже о css или javascript методе подсветки всех необходимых пунктов.
Поглядел до кучи menutrails, для меня код весьма сложным оказался для понимания, снова получают меню, ищут в нем текущий пункт, устанавливают хлебные крошки, что-то с таксономией, и organic groups. При этом еще кажется в теме в шаблоне надо что-то указать, чтобы заработало.
Итотого, уверен, что только под windows nice_menu +menutrails потратит ~500 мс на свою работу, учитывая что оба не используют кэширования и в nice_menu явно указано что блок не кэшируется. Это правда можно поправить самому, если вы точно знаете в каких случаях блок будет одинковым для пользователя.
Плюс там тоже делается сравнение _GET['q'] c href из меню,
только вот, что будет если в _GET['q'] у вас синоним, а в подсистмеме меню истинная ссылка node/xxx, он снова не найдет пункт меню и ничего не подсветит.
Правда это наверное у меня одного куча синонимов на один url
Я обычно делаю через модуль
Я знаю, как все это делается. Это знают и все нормальные разработчики. И объяснять вам никто не будет, потому что вы ничего не поймете, судя по вашему объему знаний. И дело здесь не в Друпале, а в ваших ручках. Не умеете разрабатывать вебприложения - нанимайте специалистов.
Убрала б пальченки и объяснила б мальченке. Когда-то сама была такая?
да уж, спасибо всем, теперь я понял, что с активными пунктами меню одному мне - верстальщику не справится без программиста-друпаллера. Разделение труда дает о себе знать) будешь начинать разбираться еще и с программированием помимо верстки - потеряешь профессионализм. Оказывается такая простая и необходимая на каждом сайте функция меню не так то просто дается даже программистами...
1) убедитесь через firebug или другим способом, что у нужной ссылки стоит class active, как я уже сказал, nice_menu дергает нужную функцию и он там должен быть класс
2) найти в вашей теме css и проглядеть все стили для .active
я вот к примеру для гарланд нашел такой кусочек:
ul.primary-links li a:hover, ul.primary-links li a.active {
color: #fff;
background: transparent url(images/bg-navigation-item-hover.png) no-repeat 50% 0;
}
этот класс написано для тэга a, который в составе ссылки, вам же надо как я понял разукрасить, не только a, но и li
если пока ориентироваться на изменение свойств самой ссылки то все просто, надо написать, что нибудь
типа:
class_blocka_menu ul li a.active{color:#fff}
class_blocka_menu - вот это очень хитро генерируется в nice_menu, лично я понял, что если пользователь авторизован, то
class_blocka_menu будет совпадать с именем пользователя, если нет, то по умолчанию 'Nice Menu номер_меню_если_их_несколько (Nice Menu)' или тому, что вы указали в настроках nice_menu в поле 'Menu Name', убил бы, они даже не транслитилировали насколько я понимаю его, а потом используют в качестве класса к блоку.
Лучший вариант
кроме того обычно все блоки, по крайне мере если поглядеть block.tpl.php в теме garland, выводится в div с классом
т.е. я так понимаю можно просто прописать такой css
block-nice_menus ul li a.active{color:#fff}
А чтобы изменить свойства ul, нужно использовать jquery как я указал выше, так как нельзя выделить ul элемент, который родительский по отношению к a.active.
Но это подсветит только одну ссылку, но не родительcкие ссылки, чтобы подсветить родительcкие тоже придется делать через jquery.
Но сначала убедиться что у ссылки все же выставлен класс .active, сама подсветка может и не работать при этом, но класс должен быть, его не может не быть. Точнее его может не быть если url в заголовке страницы не совпадает с тем url-ом, который вы выбираете в меню.
И еще, без анализа кода php вам не разобраться. Так как если что-то не работает, то придется разбираться почему, а причины все кроются во внутренностях.
Господи боже мой, qwaker.
Как же это у вас может работать а у меня нет?
Может я что-то не так делаю?
Зашел в админку, создал свое меню, потом вывел блок nice menu и указал ему источник - мое только что созданное меню.
первому пункту своего меню, задал ссылку на корень сайта. т.е. при переходе на главную страницу сайта, первому пункту по вашим словам должен присваиваться класс active-trail, но ничего не присваивается, как с включеным модулем Menu Trails, так и без него...
вот что у меня в адресной строке браузера:http://drupal/
а вот как на этой странице выглядит html код меню:
уважаемый, Xermit, я верстальщик, не нужно мне объяснять как верстать, я эту тему открыл, потому что класс как таковой php на сервере не генерируется и не вставляется в html. или это я что-то не так делаю, но вроде бы ссылки то совпадают, та что в меню и реальная...
вы точно уверены что найсменю, если на его основе кастомизировать простое не примари и не секондери меню, точно добавляет класс активного пункта?
может вы путаете что-то? просто я у себя перепроверил, создал меню на основе секондери линкс и указал его источником для блока модуля найсменю, там действительно активный пункт меню добавляется, т.к. он поумолчанию в друпале добавляется к пунктам меню построенным на основе секондери линкс и примари линкс. но если я делаю свое меню не на их основе, то к активному пункту никакого класса не добавляется.
sikwel@drupal.org, да хз.
Вы скорее всего сюды не заходили, или не выставили чаго? /admin/build/menu/trails
Расскажите, на основе чего делаете свое меню, прежде чем задавать вопросы. "Подсвечивание" ссылок - это задача, которая не должна быть универсальной, у каждого своя структура разделов на сайте. Добавлять атрибут типа "active" для активных ссылок, а также для всех родительских, можно в php-скриптах на уровне темизации или через джаваскрипт. Но если на вашем сайте запутанная логика, то в коде нужно учитывать все возможные варианты.
Кстати, возможны ситуации, когда для того чтобы построить "ветвь активных ссылок от дочерних до родительских", нужно делать лишнее обращение к БД, чтобы определить, к какому типу, к какому термину, к какому разделу и т.д. принадлежит текущая страница. Поэтому, если вы на этом сайте находитесь на странице топика, то не совсем целесообразно подсвечивать ссылку "Форум" в главном меню, в противном случае нужно было бы делать дополнительную проверку в коде (а оно сильно надо?).
sikwel@drupal.org, походу вы правы и menutrails работает, только если праймари иль секондари линкс. Вот это я точно применял для любого найсменю - работает. А это - понятия не имею...
Меню я создаю через админпанель друпала, отдельно каждый пункт, для каждого пункта задаю ссылку, иерархия меню простая: несколько пунктов первого уровня и некоторые пункты являются родительскими с подпунктами. дальше подпунктов родительских пунктов детализации нет. все пункты ссылаются на ноды, кроме пункта главной, в которой просто прописан адрес сайта.
кастомизирую я свое меню с помощью модуля nice menus 6.x-1.3
В любом случае нужно смотреть код...
Вот в этой теме
http://drupal.org/node/465738
на которую qwaker указал патч содержит код который как раз похож на то о чем я говорил в первых постах,
там в патче сначала собираются все пункты которые должны стать menutrails, а потом прописывает им этот класс.
так как в обычном nice_menu-6.x-1.3 этого нету.
но, я что хотел сказать, в функции nice_menu_build, чтобы создать ссылку вызывается стандартная theme_menu_item от друпала, а она в свою очередь зовет l(), код функции l():
global $language;
// Merge in defaults.
$options += array(
'attributes' => array(),
'html' => FALSE,
);
// Append active class.
if (($path == $_GET['q'] || ($path == '<front>' && drupal_is_front_page())) &&
(empty($options['language']) || $options['language']->language == $language->language)) {
if (isset($options['attributes']['class'])) {
$options['attributes']['class'] .= ' active';
}
else {
$options['attributes']['class'] = 'active';
}
}
Но у вас класс active так и не появился почему то.
Смею предположить что в _GET['q'] для корня сайта ничего не находится, так как там должна быть пустота, а в path для пункта меню не содержится
<front>
, так как вы явно указали http://drupal ? А надо было для такого пункта меню передать<front>
или вы как раз так и сделали?Для более корректного теста, сделайте пустую страницу с своим адресом, а потом посмотрите пункт меню для этой странице находясь на этой странице он по идее должен быть уже с классом .active.
а самое лучшее распечатать _GET['q'] и $path, который передается в theme('menu_item_link')...) в функции nice_menu_build, там кажется всего два таких места.
sikwel@drupal.org, специально сейчас попробовал патч, указанный здесь http://drupal.org/node/465738. Всё замечательно работает
Если не лады с английским:
1. Качаете патч с 11-го коммента приведенной выше страницы
2. пропатчиваете модуль nicemenu (о том, как это делать, еси не в курсе - указано здесь
3. После этого вы работаете с классом active-trail и темизируете как надо:
3.1. для дочерних меню класс active-trail
3.2. для родительских menuparent active-trail.
у меня наверное друпал заколдованный)) проделал все как вы сказали - никакого класса не появилось))
я уже и ноду повесил на пункт меню чтобы убедиться, нифига, перехожу на эту ноду и никакого класса не добавляется...
потратил даже пару часов чтобы разобраться как патчить через patch под винду))
потом еще и руками все перерпроверил, файл пропатчился все замечательно, но ничего не работает))
Все кэширующее и оптимизирующее выключено? Начни с простого, в nice_menu_build впиши ручками куда нибудь print('AAAA'), просто, чтобы убедится, что твои изменения в этом файле отражаются на выводе друпала, если нет, то ты не тот файл возможно редактируешь.
надеюсь у тебя не включен APC и eAccelerator в php c флагом mktime='0', иначе даже после рестарта апача кэшириующий оптимизатор не поймет что php код давно обновился и по прежнему будет загружать старый закэшированный код.
да вроде никакого сверхъестественного кеширования у меня не включено, к примеру изменяю файл темплейт пхп (переопределяю функцию темизации найс меню для вывода классов для первого и последнего пунктов) и все тут же изменяется. (эту функцию темизации на время попыток отобразить класс активного меню я убрал от греха подальше)
кстати, когда я перехожу на ноду, в цепочке навигации она ведь должна отображаться? у меня почему-то там как была домашняя страница(Home › ) , так и осталась...
Ну смотрите: если пропатчился, значит по любому есть класс active-trail. Тут даже ведь и ошибиться негде.
Возьмите firebug, и посмотрите, какой класс присваивается активным пунктам меню -родительскому и дочернему?
если хотите, пишите в личку сайт, посмотрю
в любом месте той функции nice_menu_build, она в nice_menu.module
впишите print('AAA'), если в начале страницы вы увидите AAA
то значит все норм и ваш патч наложился и все должно работать,
только я думаю может у вас кэшируется это и в результате выполняется либо старый код от nice_menu
либо вы не в том месте файл пропатчили
отправил в личку, получили?
создал простое меню на основе секондери линкс в блоке, вывел туда ноду, все прекрасно работает, модуль меню трейл добавляет класс активного пункта (элемента списка li), также класс по-умолчанию для секондери добавляется к ссылкe. В моем меню по-прежнему к этому пункту ничегоне добавляется... значит не работает в моих условиях этот патч(
Провел еще один эксперимент, применил модуль найсменю к этому меню которое на секондери линкс, как известно у секондери линкс активный класс добавляется по-умолчанию без каких бы то нибыло модулей к тегу ссылки, просто active. Я вывел этом меню через блок модуля найсменю, который был пропатчен и вуаля, у элемента li активного пункта, добавлися класс active-trail.
Беру и заменяю пропатченный файл найсменю на родной, который без изменений. перегружаю страницу и вижу - класс active-trail благополучно исчез, остался только по-умолчанию который у ссылки...
вот такие вот дела... патч и модуль работают.. значит дело в созданном мною меню... а создавал я его правильно..
ИТС ЭЛАЙВ!!!))) Мытарства окончены))) дело было опять в мелочи и моих кривых руках))
я в пункте меню на главную и на ноду ставил полный путь, т.е. http://drupal/node/6, а если так задавать, то ничего не работает)
поставил на ноду: node/6
на главную: <front>
и все прекрасно заработало, класс добавляется))
спасибо всем огромное за ответы и терпение (;
эх, а ведь говорил проверьте соответствие, что в _GET['q'] и что в меню указываете.
Скачиваешь "Menu position" и выбираешь свои меню, создаешь их и ставишь галочку на "Mark the rule's parent menu item as being "active"."ВсеЮ проблема решена, работает.