Подтвердить что ты не робот

Измените параметры маршрута без перезагрузки в angular 2

Я делаю сайт недвижимости с помощью angular 2, google maps и т.д., и когда пользователь меняет центр карты, я выполняю поиск в api, указывающий текущую позицию карты, а также радиус. Дело в том, что я хочу отразить эти значения в URL-адресе без перезагрузки всей страницы. Это возможно? Я нашел некоторые решения, используя AngularJS 1.x, но ничего о angular 2.

4b9b3361

Ответ 1

Вы можете использовать location.go(url), который в основном изменит ваш URL-адрес, без изменения маршрута приложения.

ПРИМЕЧАНИЕ это может привести к другому эффекту, например перенаправлению на детский маршрут с текущего маршрута.

Связанный вопрос, который описывает location.go, не будет интимным для Router, чтобы произойти изменения.

Ответ 2

Начиная с RC6, вы можете сделать следующее, чтобы изменить URL без изменения состояния и, таким образом, сохранить историю маршрутов.

import {OnInit} from '@angular/core';

import {Location} from '@angular/common'; 
// If you dont import this angular will import the wrong "Location"

@Component({
  selector: 'example-component',
  templateUrl: 'xxx.html'
})
export class ExampleComponent implements OnInit
{
  constructor( private location: Location )
  {}

  ngOnInit()
  {    
    this.location.replaceState("/some/newstate/");
  }
}

Ответ 3

Использование location.go(url) - это путь, но вместо router.createUrlTree() url, рассмотрите возможность его генерации с помощью router.createUrlTree().

Учитывая, что вы хотите сделать следующий вызов маршрутизатора: this.router.navigate([{param: 1}], {relativeTo: this.activatedRoute}) но без перезагрузки компонента его можно переписать как:

const url = this
        .router
        .createUrlTree([{param: 1}], {relativeTo: this.activatedRoute})
        .toString();

 this.location.go(url);

Ответ 4

У меня были серьезные проблемы с тем, чтобы заставить это работать в RCx выпусках angular2. Пакет Location был перемещен, и запуск location.go() внутри constructor() работать не будет. Это должен быть ngOnInit() или позже в жизненном цикле. Вот пример кода:

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

@Component({
  selector: 'example-component',
  templateUrl: 'xxx.html'
})
export class ExampleComponent implements OnInit
{
  constructor( private location: Location )
  {}

  ngOnInit()
  {    
    this.location.go( '/example;example_param=917' );
  }
}

Вот angular ресурсы по этому вопросу:https://angular.io/docs/ts/latest/api/common/index/Location-class.html https://angular.io/docs/ts/latest/api/common/index/LocationStrategy-class.html

Ответ 5

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

У меня была похожая проблема, и я сначала попытался использовать location.go и location.replaceState, как это было предложено в других ответах здесь. Однако я столкнулся с проблемами, когда мне пришлось перейти на другую страницу в приложении, потому что навигация была относительно текущего маршрута, а текущий маршрут не обновлялся с помощью location.go или location.replaceState (маршрутизатор ничего не знает о том, что они делают на URL)

По сути, мне нужно было решение, которое НЕ загружало страницу/компонент при изменении параметра маршрута, но обновляло внутреннее состояние маршрута.

Я закончил с использованием параметров запроса. Вы можете найти больше об этом здесь: https://angular-2-training-book.rangle.io/handout/routing/query_params.html

Поэтому, если вам нужно что-то вроде сохранения заказа и получения идентификатора заказа, вы можете обновить URL своей страницы, как показано ниже. Обновление местоположения центра и связанных данных на карте будет аналогичным

// let say we're saving an order. Initally the URL is just blah/orders
save(orderId) {
    // [Here we would call back-end to save the order in the database]

    this.router.navigate(['orders'], { queryParams: { id: orderId } });
    // now the URL is blah/orders?id:1234. We don't reload the orders
    // page or component so get desired behaviour of not seeing any 
    // flickers or resetting the page.
}

и вы отслеживаете это в методе ngOnInit, например:

ngOnInit() {
    this.orderId = this.route
        .queryParamMap
        .map(params => params.get('id') || null);
    // orderID is up-to-date with what is saved in database now, or if
    // nothing is saved and hence no id query paramter the orderId variable
    // is simply null.
    // [You can load the order here from its ID if this suits your design]
}

Если вам нужно перейти прямо на страницу заказа с новым (несохраненным) заказом, вы можете сделать:

this.router.navigate(['orders']);

Или, если вам нужно перейти прямо на страницу заказа для существующего (сохраненного) заказа, вы можете сделать:

this.router.navigate(['orders'], { queryParams: { id: '1234' } });

Ответ 6

Я использую этот способ, чтобы получить его:

const queryParamsObj = {foo: 1, bar: 2, andThis: 'text'};

this.location.replaceState(
  this.router.createUrlTree(
    [this.locationStrategy.path().split('?')[0]], // Get uri
    {queryParams: queryParamsObj} // Pass all parameters inside queryParamsObj
  ).toString()
);

- ОБНОВЛЕНИЕ -

Я думаю, что я должен добавить еще немного информации для этого.

Если вы используете this.location.replaceState(), маршрутизатор вашего приложения не обновляется, поэтому, если вы используете информацию о маршрутизаторе позже, она не будет равна этому в вашем браузере. Например, если вы используете localizeService для изменения языка, после переключения языка ваше приложение возвращается к последнему URL-адресу, на котором вы находились до этого, с помощью this.location.replaceState().

Если вам не нужно это поведение, вы можете выбрать другой метод для обновления URL, например:

this.router.navigate(
  [this.locationStrategy.path().split('?')[0]],
  {queryParams: queryParamsObj}
);

В этом варианте ваш браузер также не обновляется, но ваше изменение URL также внедряется в Router вашего приложения, поэтому при переключении языка у вас нет проблем, как в this.location.replaceState().

Конечно, вы можете выбрать метод для ваших нужд. Первый способ легче, потому что вы не используете приложение больше, чем меняете URL в браузере.

Ответ 7

Для меня это было фактически сочетание обоих с Angular 4.4.5.

Использование router.navigate продолжает уничтожать мой url, не уважая realtiveTo: activatedRoute часть.

Я закончил с:

this._location.go(this._router.createUrlTree([this._router.url], { queryParams: { profile: value.id } }).toString())