Angular: как определить активный маршрут с параметрами?

Я прочитал этот вопрос о том, как определить активный route, но все же мне непонятно, как определить активный маршрут с параметрами?

Прямо сейчас я делаю это так:

<a [routerLink]="['/Profile/Feed', {username: username}]"
   [ngClass]="{active: getLinkStyle('/profile/john_doe/feed')}">
   Feed for {{username}}
</a>

И внутри моего компонента:

getLinkStyle(path:string):boolean {
  console.log(this._location.path()); // logs: '/profile/john_doe/feed'
  return this._location.path() === path;
}

И это будет работать, потому что я передаю имя пользователя в виде строки. Есть ли способ сделать это с передачей правильного параметра??


person Aico Klein Ovink    schedule 02.01.2016    source источник
comment
Вы можете внедрить $routingPatams в свой контроллер и получить параметр из своего маршрута.   -  person CyberAleks    schedule 03.01.2016
comment
Да, я знаю, на самом деле username из RouteParams. Но как я могу передать это из своего HTML в свой компонент? @КиберАлекс   -  person Aico Klein Ovink    schedule 03.01.2016
comment
То, что я хочу сделать, это что-то вроде: [ngClass]="{active: getLinkStyle('/profile/{{username}}/feed')}", но, конечно, это не сработает..   -  person Aico Klein Ovink    schedule 03.01.2016
comment
Вы можете сделать это как '/profile/'+username+'/feed'   -  person CyberAleks    schedule 03.01.2016
comment
Да, спасибо @CyberAleks. Пробовал, но мой редактор не дал ему правильных цветов синтаксиса.. Так что не проверял, тупица, ха-ха! Спасибо!   -  person Aico Klein Ovink    schedule 03.01.2016


Ответы (7)


Просто проверьте автоматически определенный класс router-link-active для элемента a.

person iuristona    schedule 27.01.2016
comment
Они реализовали это в бета-версии 2? - person Aico Klein Ovink; 28.01.2016
comment
Можно ли автоматически установить класс active, если применяется класс router-link-active? Потому что для большинства шаблонов CSS потребуются другие имена классов, и я не хочу изменять шаблон. @AicoKleinOvink Afaik это уже было в последних альфа-версиях. - person berhir; 28.01.2016
comment
Они реализованы на версии 2.0.0-alpha.37 (2015-09-09), чтобы быть точно. github.com/angular/angular/issues/3209 - person iuristona; 28.01.2016
comment
Я не мог изменить имя css по умолчанию, оно жестко закодировано. Я видел, что существует логическое свойство isRouteActive: для каждого [routerLink], но я не могу сослаться на него. - person iuristona; 28.01.2016
comment
Кажется, директива routerLinkActive работает только с Link Params( /foo/bar ), но не с Query Params ( /foo;value=bar ). - person Francis.TM; 08.07.2016

С новым, перспективным маршрутизатором Angular 2 (в версии 3.0-alpha.7, когда я пишу это), это очень просто.

Все, что вам нужно сделать, это использовать директиву [routerLinkActive] в вашей ссылке.

<a [routerLinkActive]="['active']" [routerLink]="['/contact',  contact.id ]">
    {{contact.name}}
</a>

Это то, что вы будете использовать, когда Angular 2 будет выпущен по-настоящему, а не кандидатом на выпуск. Я использую альфа-версию маршрутизатора сейчас и не имею никаких проблем.

Это демонстрирует Plunk. Вы можете видеть, что ссылки становятся красными, когда вы нажимаете на них. Это директива, присваивающая им класс active. Конечно, вы можете использовать любое имя класса по вашему выбору.

person Michael Oryl    schedule 24.06.2016
comment
Вау, теперь так просто! Это должен быть принятый ответ. - person Lee Richardson; 25.06.2016

В Angular 2 rc1 router.isRouteActive больше не существует. Мне нигде не удалось найти работающее решение, но я смог решить его следующим образом (специальный метод isActiveRoute делает свое дело):

App.component.ts:

import { Component } from '@angular/core';
import { Routes, Route, Router, ROUTER_DIRECTIVES, ROUTER_PROVIDERS } from '@angular/router';
import { HomeComponent } from './home.component';
import { P1Component } from './p1.component';

@Component({
    selector: 'app',
    templateUrl: './app/app.template.html',
    directives: [ROUTER_DIRECTIVES]
})

@Routes([
    { path: '/', component: HomeComponent },
    { path: '/p1', component: P1Component }
])

export class AppComponent implements OnInit {

    constructor(public router: Router){ }

    isActiveRoute(route: string) {
        return this.router.serializeUrl(this.router.urlTree) == this.router.serializeUrl((this.router.createUrlTree([route])));
    } 
}

Приложение.template.html:

            <ul class="nav navbar-nav">
                <li [class.active]="isActiveRoute('/')">
                    <a class="nav-link" [routerLink]="['/']">Home</a>
                </li>
                <li [class.active]="isActiveRoute('/p1')">
                    <a class="nav-link" [routerLink]="['/p1']">Page 1</a>
                </li>
person Mcanic    schedule 28.05.2016
comment
Как настроить функцию isActiveRoute для поддержки параметров маршрута? - person chenk; 20.07.2016

Я пытался установить класс active без необходимости точно знать текущее местоположение (используя имя маршрута). Это лучшее решение, которое у меня есть до сих пор.

Вот как RouteConfig выглядит (я немного изменил его, чтобы он выглядел так, как вы хотите):

@RouteConfig([
  { path: '/', component: HomePage, as: 'Home' },
  { path: '/signin', component: SignInPage, as: 'SignIn' },
  { path: '/profile/:username/feed', component: FeedPage, as: 'ProfileFeed' },
])

И View будет выглядеть так:

<li [class.active]="router.isRouteActive(router.generate(['/Home']))">
   <a [routerLink]="['/Home']">Home</a>
</li>
<li [class.active]="router.isRouteActive(router.generate(['/SignIn']))">
   <a [routerLink]="['/SignIn']">Sign In</a>
</li>
<li [class.active]="router.isRouteActive(router.generate(['/ProfileFeed', { username: user.username }]))">
    <a [routerLink]="['/ProfileFeed', { username: user.username }]">Feed</a>
</li>

До сих пор это было моим предпочтительным решением проблемы, оно может быть полезно и для вас.

person Alex Santos    schedule 02.01.2016
comment
Выглядит многообещающе, завтра займусь этим!! Очень признателен! - person Aico Klein Ovink; 03.01.2016
comment
Все еще думаю, что что-то вроде ui-sref-active от удивительного ui-router было бы здорово. - person Aico Klein Ovink; 03.01.2016
comment
Хорошо, я попробовал ваше решение @Alex, но не могу заставить его работать. Это фактическая часть моего кода: <a class="main" [routerLink]="['/Profile/Feed', {username: profileUser.username}]" [class.active]="router.isRouteActive(router.generate(['/Profile/Feed', {username: profileUser.username}]))"> <h3><span class="fa fa-home"></span></h3> Profiel </a> - person Aico Klein Ovink; 05.01.2016
comment
Это выглядит правильно, вы случайно не получаете ошибки (если да, то какие бы они были)? Напоминаем, вам нужно импортировать файл Router. import {ROUTER_DIRECTIVES, Router} from 'angular2/router'; - person Alex Santos; 05.01.2016
comment
Когда я console.log(router.generate(['/Profile/Feed', {username: profileUser.username}]) возвращаю этот объект: ResolvedInstruction {auxInstruction: Object, component: ComponentInstruction, child: ResolvedInstruction} - person Aico Klein Ovink; 05.01.2016
comment
Не могли бы вы также поделиться своим RouteConfig? Глядя на название вашего маршрута, кажется, что Feed является подкомпонентом Profile. (Отредактировано, смешал мои мысли) - person Alex Santos; 05.01.2016
comment
Что касается вывода функции генерации, он выглядит правильно, я только что проверил то, что вы мне прислали, в приложении angular 2, и все работает нормально. Вот что у меня есть: gist.github.com/Colex/658e534159027ecfc60b - person Alex Santos; 05.01.2016
comment
Вот моя суть, для протокола: я переписал его обратно на старый путь.. Может быть, вы можете посмотреть! - person Aico Klein Ovink; 06.01.2016
comment
@AlexCorreiaSantos Это работает. Спасибо! Я хотел бы знать, как вводится router:Router? Поскольку класс Router не появляется ни в одном массиве providers, как Angular может знать, что вводить? - person LShi; 17.04.2016
comment
@ LS.Shanghai Вы можете просто добавить public router: Router в качестве аргумента в конструктор компонента. - person František Žiačik; 15.05.2016
comment
В Angular2 rc1 вам нужно обновить что-то вроде этого: [class.active]="router.urlTree.contains(router.createUrlTree(['Home']))" - person František Žiačik; 15.05.2016

Вы можете использовать новую службу определения местоположения из общего пакета Angular2: https://angular.io/docs/js/latest/api/router/Location-class.html#!#path-anchor

import { Location } from '@angular/common';

...

export class YourClass {
    constructor(private _loc:Location) {}

    getCurrentPath() {
        return this._loc.path();
    }
}

Примечание. Лучше использовать службу маршрутизатора для запуска изменений маршрута. Используйте Location только в том случае, если вам нужно взаимодействовать или создавать нормализованные URL-адреса вне маршрутизации.

Обратите внимание: в документации говорится об импорте из router, но последняя бета-версия, которая у меня есть, имеет Location службы в common.

person Brian    schedule 09.06.2016

попробуй это :

<li   class="ann_profileimg" [routerLinkActive]="['active']" [routerLink]="['profile']">
            <div class="ann_header_menu_left ann_profile_avatar_small"></div>
            <span>Vishnu </span>
          </li>
person VISHNU Radhakrishnan    schedule 23.10.2017

Для Angular версии 4+ определение активного маршрута в шаблоне довольно просто, поскольку для этой цели существует встроенная директива с именем routerLinkActive, которую вы можете использовать следующим образом:

      <li class="nav-item" routerLinkActive="active">
        <a class="nav-link" routerLink="/home">Home</a>
      </li>
      <li class="nav-item" routerLinkActive="active">
        <a class="nav-link" routerLink="/about-us">About Us</a>
      </li>
      <li class="nav-item" routerLinkActive="active">
        <a title="Contact Us" class="nav-link " routerLink="/contact-us">Contact</a>
      </li>
    </ul>
person asmmahmud    schedule 11.10.2017