强制方法等待标记创建之前调用回调方法中的下一个方法

时间:2021-02-02 17:31:23

标签: javascript typescript google-maps async-await promise

我正在使用 Google 地图库制作一个应用程序,并带有一个调用两组进程的回调函数。

我想确保在启动第二个进程之前完成第一个进程。

这意味着我希望 callbackHandler 方法在调用 calculateAndDisplayRoute() 之前等待在方法 createChargerPointMarkers() 中创建的所有标记在地图上创建、推送和设置,但事实并非如此。

相反,它会耐心等待直到最后一个循环,但在最后一个循环真正完成之前启动了 calculateAndDisplay 方法

假设你有 3 个循环,会发生什么: “循环 1 出 3” (您可以看到在地图上设置的标记) “循环 2 出 3” (您可以看到在地图上设置的标记) “循环 3 出 3” “EV标记创作完成” “路线计算开始” 只有在此之后,您才会看到最后一个循环的标记被创建并设置在地图上。

我想我错误地组织了承诺/等待。如何强制编译器在继续之前等待所有标记创建和设置?

备注:很难/不可能展示一个可重现的功能示例,因为折线创建方法使用外部库(epolys.js,非常有用),没有它,CodePen 和 JSFiddle 无法理解代码。您还需要更多的代码来创建 Google 地图、标记等。所以这里放的代码太多了

如果您愿意查看整个代码,我可以共享该存储库,但它很长(到目前为止有 441 行)并且只有我在此处放置的方法与此问题相关。

chargingPointsMarkers = [];
markerArray = [];

async callbackHandler(startEndPointsArray, calculateAndDisplayRoute): Promise<void> {
    await this.setChargingStationsMarkers();
    calculateAndDisplayRoute();
  }

  calculateAndDisplayRoute(): Promise<void> {
    console.log('calculation started')
  }

  async setChargingStationsMarkers(): Promise<void> {

    const polyline = await this.createPolyline();
    const polylineMarkersArray = await this.createMarkersOnPolyline(polyline);
    // This makes a Google Polyline object.I voluntarily did not include the polyline methods, 
   // they are not relevant and are resolved before the following loop starts

    const baseUrl = 'https://api.openchargemap.io/v3/poi/output=json&maxresults=100&verbose=false&includecomments=true';

    for (let j = 0; j < polylineMarkersArray.length - 1; j++) {

      const origin = polylineMarkersArray[j].getPosition();
      const destination = polylineMarkersArray[j + 1].getPosition();

      const route = await this.createRoute(origin, destination);

      const encodedPolyline = route.overview_polyline;
      const queryUrl = baseUrl + '&polyline=' + encodedPolyline + '&distance=50';

      await fetch(queryUrl)
        .then((response) => response.json())
        .then( async (data) => await this.createChargerPointMarkers(data))
        .then (() => {
                   const k = j + 1;
          const l = polylineMarkersArray.length - 1;
          if (j === polylineMarkersArray.length - 2) {
            console.log('loop ' + k + ' of ' + l);
            console.log('EV markers creation finished');
          }else{
            console.log('loop ' + k + ' of ' + l);
          }
        });

    }
  }

async createChargerPointMarkers(jsonChargingPoints): Promise<void> {
    // Convert the Json response elements to Google Markers, places them on the Map and pushes them to an array.
    for (const item of jsonChargingPoints) {
      const LatLng = new google.maps.LatLng(parseFloat(item.AddressInfo.Latitude), parseFloat(item.AddressInfo.Longitude));
      const marker = await new google.maps.Marker({
        position: LatLng,
        map: this.map,
        draggable: false,
      });
      this.markerArray.push(marker);
      this.chargingPointsMarkers.push(marker);
    }
  }

  async createRoute(point1, point2): Promise<google.maps.DirectionsRoute> {
    // Returns a Google DirectionsRoute object
    const directionsService = new google.maps.DirectionsService();
    const request = {
      origin: point1,
      destination: point2,
      travelMode: google.maps.TravelMode.DRIVING,
      unitSystem: google.maps.UnitSystem.METRIC
    };
    return new Promise(resolve => directionsService.route(request,
      (result, status) => {
        if (status === 'OK') {
          resolve(result.routes[0]);
        } else {
          window.alert('Directions request failed due to ' + status);
        }
      })
    );
  }

0 个答案:

没有答案