Angular GoogleMap not setting bounds properly when coming out of hidden state

Discussão em 'Angular' iniciado por Christian, Fevereiro 26, 2025.

  1. Christian

    Christian Guest

    I have a component which visualize some data in an mat accordion, next to it is a google map which shows the location of each data point. On top of the component I have a dropdown, depending on the selection project data is refreshed and the accordion + map should update.

    The map is its own component and data is shared via a service. I don't want to show the map when there is no data to visualize. I would like to work with [hidden] instead of ngIf because I dont need a new map instance in that case.

    My current problem is that when the map is in a hidden state, then I change the drop down selection, project data gets updated and I have actual data, map is visible again, markers are shown but the map is fully zoomed out with with grey borders on the top and the bottom.

    I can get it to work with ngIf and ChangeDetectorRef which probably is not best practice and I may have an error somewhere.

    Template:

    <div [hidden]="!projects || (projects && projects.length == 0)" class="right-panel" style="border-radius: 16px; overflow: hidden">
    <app-map (markerClicked)="setExpandedPanel($event)"></app-map>
    </div>


    Map Component Template:

    <div style="width: 100%; height: 100%; min-height: 750px">
    <input id="pac-input" #placesContainer style="margin-top: 10px" type="text"/>
    <google-map (mapInitialized)="onMapReady($event)" mapId="myMap" [zoom]="zoom"
    ="center"
    width="100%" height="100%">

    @for (marker of projectMarkers; track marker.position) {
    <map-advanced-marker (mapClick)="onMarkerClick(marker.id)"
    [position]="marker.position"
    [content]="marker.icon"
    [zIndex]="marker.zIndex"
    />
    }
    </google-map>
    </div>


    Map Component:

    zoom: number = 7;
    center: google.maps.LatLngLiteral = ..

    projects: Project[] = [];

    @Output() markerClicked = new EventEmitter<string | null>();

    private mapReady$ = new BehaviorSubject<boolean>(false);

    projectMarkers: CustomMapMarker[] = [];
    currentExpandedProjectId: string | null = null;

    markerSvgString = '<svg width="62" height="78" ..</g></svg>';

    @ViewChild('placesContainer') placesElement!: ElementRef;
    private map!: google.maps.Map;

    constructor(
    private projectStateService: ProjectStateService,
    private mapService: MapBaseService,
    private ref: ChangeDetectorRef
    ) {}

    ngAfterViewInit(): void {
    combineLatest([
    this.projectStateService.projects$,
    this.mapReady$
    ]).subscribe(([ projects, mapReady]) => {
    if(mapReady && projects && projects.length > 0){
    this.projects = projects!;
    this.setProjectMarkers();
    this.setBounds();
    this.ref.detectChanges()
    }
    });
    }

    async onMapReady(map: google.maps.Map): Promise<void> {
    await this.mapService.loadMapLibraries()
    this.map = map;
    this.map.setOptions({
    gestureHandling: 'cooperative',
    fullscreenControl: false,
    mapTypeControl: true,
    mapTypeControlOptions: {
    style: google.maps.MapTypeControlStyle.HORIZONTAL_BAR,
    position: google.maps.ControlPosition.TOP_RIGHT
    }
    });
    await this.mapService.initPlacesSearch(map, this.placesElement);
    this.mapReady$.next(true);
    }


    Just switching between drop down selections with different projects works perfectly, its all about the switch of no projects > hidden map to projects > visible map.

    Continue reading...​

Compartilhe esta Página