Как инициализировать свойство в сервисе для набора компонентов? - PullRequest
1 голос
/ 05 февраля 2020

Мой сервис выглядит так:

export class UserService {
  constructor() {}

  coords: Coordinates;

  getPosition() {
    navigator.geolocation.getCurrentPosition(position => {
      this.coords = [position.coords.latitude, position.coords.longitude];
    });
  }
}

Я инициализирую свойство coords, вызывая getPosition() метод

И у меня есть несколько компонентов. Все эти компоненты используют это свойство. Поэтому я хочу вызвать userService.getPosition (), когда создаю экземпляр любого из этих компонентов. Но для других компонентов переменная должна оставаться нетронутой.

Все эти компоненты являются частью моего DashboardModule, который импортирует DashboardRouting. И DashboardRouting выглядит следующим образом:

const routes: Routes = [
  {
    path: '',
    component: WallComponent,
  },
  {
    path: 'places',
    component: PlacesComponent,
  },
  {
    path: 'object/:id',
    component: ObjectComponent,
  },
  {
    path: '**',
    redirectTo: '',
    pathMatch: 'full',
  },
];

@NgModule({
  imports: [RouterModule.forChild(routes)],
  exports: [RouterModule],
})
export class DashboardRoutingModule {
  constructor() {
    console.log('DashboardRoutingModule');
  }
}

Если вы посмотрите внимательно, Routing использует эти компоненты: WallComponent PlacesComponent ObjectComponent

Все эти компоненты (страницы) используют свойство UserService.coords. Так что это должно быть инициализировано. Таким образом, метод должен вызываться в каждом из компонентов в методе ngOnInit () - но я хочу обернуть все эти компоненты в один родительский компонент, который будет только инициализировать свойство UserService.coords (вызовет метод UserService.getPosition () ).

Как мне переделать это?

Ответы [ 3 ]

0 голосов
/ 05 февраля 2020

Если вы предоставляете услугу в глобальном масштабе, она будет одноэлементной, поэтому любой компонент или служба будут иметь доступ к одному и тому же экземпляру, поэтому они будут видеть изменения друг друга. Но если вы предоставляете услугу в компоненте (см. DashboardWrapperComponent ниже), она создаст новый экземпляр для этого компонента и его дочерних элементов независимо от того, существует ли глобально предоставленный экземпляр или нет. В этом случае только дочерние компоненты будут видеть изменения друг друга.

Так что это должно решить требование для других компонентов, переменная должна оставаться нетронутой .

@Component({
    selector: 'app-dashboard-wrapper',
    template: `
        <div>
            <app-child></app-child>
        </div>
    `,
    provide: [
        FancyService,
    ]
})
export class DashboardWrapperComponent {

}

Но в настоящее время у вас нет общего родителя для тех страниц, на которых вы хотите иметь экземпляр общего сервиса. Это может быть достигнуто следующим образом:


const routes: Routes = [
  {
    path: 'home',
    component: DashboardWrapperComponent,
    children: [
      {
        path: '',
        component: WallComponent,
      },
      {
        path: 'places',
        component: PlacesComponent,
      },
      {
        path: 'object/:id',
        component: ObjectComponent,
      },
    ],
  },
  {
    path: '**',
    redirectTo: 'home',
    pathMatch: 'full',
  },
];

@Component({
    selector: 'app-dashboard-wrapper',
    template: `
        <router-outlet></router-outlet>
    `,
    provide: [
        FancyService,
    ]
})
export class DashboardWrapperComponent {

}

Я знаю, что у вас '' как маршрут root, я не уверен, что вы можете иметь '' на 2 уровнях маршрутов, например , для DashboardWrapperComponent и WallComponent, поэтому я добавил туда 'home'.

0 голосов
/ 06 февраля 2020

Решил это, создав DashboardComponent с шаблоном: <router-outlet></router-outlet>

и изменив маршрут следующим образом:

const routes: Routes = [
  {
    path: '',
    component: DashboardComponent,
    children: [
      {
        path: 'wall',
        component: WallComponent,
      },
      {
        path: 'places',
        component: PlacesComponent,
      },
      {
        path: 'object/:id',
        component: ObjectComponent,
      },
      {
        path: '**',
        redirectTo: 'wall',
        pathMatch: 'full',
      },
    ],
  },
];
0 голосов
/ 05 февраля 2020

логически каждый раз, когда вызывается метод getPosition(), свойство coords будет обновляться; если вы хотите установить его только один раз, вы можете инициализировать его как null, а затем установить его один раз, когда getPosition() вызвал для в первый раз, то есть:

export class UserService {
  coords: Coordinates | null = null;

  getPosition() {
    navigator.geolocation.getCurrentPosition(position => {
      if (this.coords === null) {
          this.coords = [position.coords.latitude, position.coords.longitude];
      }
    });
  }
}

надеюсь, это поможет вам выбрать правильный путь: -)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...