OpenLayers 5 |Угловой 7 |Угловой материал |Карта не работает внутри углового материала мат-степпера - PullRequest
0 голосов
/ 16 февраля 2019

Я импортировал карту OpenLayers в файл TS своего компонента, затем я создал блок div с id = map, где должна отображаться карта OpenLayers, но это не так.Когда я переместил блок div (#map) за пределы блоков mat-stepper, он работает.

Component.ts:

import { Component, OnInit } from '@angular/core';
import { FormBuilder, FormGroup, Validators } from '@angular/forms';

import OlMap from 'ol/Map';
import OlXYZ from 'ol/source/XYZ';
import OlTileLayer from 'ol/layer/Tile';
import OlView from 'ol/View';
import { fromLonLat } from 'ol/proj';

@Component({
  selector: 'app-sell',
  templateUrl: './sell.component.html',
  styleUrls: ['./sell.component.scss'],
})
export class SellComponent implements OnInit {
  ...

  map: OlMap;
  source: OlXYZ;
  layer: OlTileLayer;
  view: OlView;

  ...

  ngOnInit() {
    this.source = new OlXYZ({
      url: 'http://tile.osm.org/{z}/{x}/{y}.png',
    });

    this.layer = new OlTileLayer({
      source: this.source,
    });

    this.view = new OlView({
      center: fromLonLat([6.661594, 50.433237]),
      zoom: 3,
    });

    this.map = new OlMap({
      target: 'map',
      layers: [this.layer],
      view: this.view,
    });
  }

Component.html:

<mat-horizontal-stepper
  linear
  labelPosition="bottom"
  #stepper
  class="sell-form-container"
>
  <mat-step ...>
    <form ...>
      ...
      <div id="map"></div>  //<- here it does not work, map does not display
      ...
    </form>
  </mat-step>
  ...
</mat-horizontal-stepper>
<div id="map"></div> //<- here it works, map displays

Component.css:

#map {
  width: 100%;
  height: 500px;
}

Что не так в моем коде?

1 Ответ

0 голосов
/ 16 февраля 2019

Я полагаю, что ваша проблема связана с содержимым, к которому вы пытаетесь прикрепить OLMap, к включенному содержимому mat-stepper или mat-step.

В жизненном цикле компонента дочерний компонентне готов на шаге OnInit родителя.Поскольку вы помещаете нужный div в компонент mat, он вместо этого включается в жизненный цикл этого компонента.

Один из способов решить эту проблему - работать с методом жизненного цикла ngAfterViewInit.Наличие вашего кода в этом методе должно решить эту проблему.

ngAfterViewInit() {
  this.map = new OlMap({
    target: 'map',
    layers: [this.layer],
    view: this.view,
  });
}

Я бы хотел представить другой способ работы с компонентами, а также ради потенциального любопытства.Следя за включенным контентом, если нужный элемент находится в текущем компоненте, вы должны использовать декоратор ViewChild, чтобы выбрать его.В противном случае, если он находится в дочернем компоненте, используйте декоратор ContentChild.

// html
<mat-horizontal-stepper ...>
  <mat-step ...>
    <form ...>
      ...
      <div #myMapRef id="map"></div>
      ...
    </form>
  </mat-step>
  ...
</mat-horizontal-stepper>

// parent ts
@ContentChild('myMapRef') // <-- if it's in a child component, your case should use this
@ViewChild('myMapRef') // <-- if it's in this component, your "this is working" would use this
myMap: ElementRef;

ngAfterViewInit() {
  console.log(this.myMap); // can get the ID from the ElementRef
}

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

...