Leaflet でデータを検査します

この章では、 Leaflet JS を使用して、ここに用意されている Optimized Map for Visualization Plus (ビジュアル化に最適化した地図 Plus )ベース マップまたは任意の Leaflet でサポートされているマッププロバイダの上にある HERE platform カタログレイヤーから GeoJSON または Protobuf でエンコードされたデータを表示する方法について説明します。

データ インスペクター ライブラリには、プラットフォームデータを操作するための Leaflet の使用法を示す 2 つのがあります。

  • このleaflet / geojson例では、 JavaScript を使用して HERE platform で認証し、 HERE Data SDK for TypeScript を使用して HERE GeoJSON サンプルカタログの GeoJSON データにアクセスする方法、および Leaflet 用の HARP プラグインを使用してビジュアル化に最適化した地図 Plus ベース マップを表示する方法を示します。 また、ベース マップ上でデータを視覚化する方法についても説明します。

    Leaflet による GeoJSON データの視覚化
    図 1. Leaflet による GeoJSON データの視覚化
  • leaflet / protobuf この例では、上記の例と同じ HERE platform 認証およびベース マップレンダリングメカニズムを示します。 唯一の違いは leaflet / protobuf、 Protobuf でエンコードされた道路 - トポロジ & ジオメトリレイヤーのデータに HERE Map Content カタログからアクセスする方法、レイヤーからスキーマを取得して GeoJSON にデコードする方法を示している点です。 ベース マップでデータをレンダリングする方法についても説明します。

    Leaflet でエンコードされたデータの視覚化
    図 2. Leaflet でエンコードされたデータの視覚化

サンプルの Web アプリを作成します

Leaflet でプラットフォームデータの視覚化を実装するシンプルなアプリを作成するには、次の手順を実行します。

  1. 空の HTML ファイルを作成します。
  2. 使用するベース マップと、表示するプラットフォームデータのタイプ( GeoJSON または Protobuf でエンコードされたデータ)に応じて <head> 、必要なライブラリを HTML のセクションに追加します。

    • リーフレットライブラリ

      <script src="https://cdnjs.cloudflare.com/ajax/libs/leaflet/1.5.1/leaflet.js" charset="utf-8"></script>
      
    • Three.js ライブラリharp.gl ライブラリおよび harp.gl プラグイン for Leaflet で HERE ビジュアル化に最適化した地図 Plus ベース マップを視覚化します。

      <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/104/three.js" charset="utf-8"></script>
      <script src="https://unpkg.com/@here/harp.gl@0.10.0/dist/harp.js" charset="utf-8"></script>
      <script src="https://unpkg.com/@here/harp-leaflet@0.1.1/build/harp-leaflet.js" charset="utf-8"></script>
      
    • HERE Data SDK for TypeScript ライブラリ :

      • olp-sdk-authentication プラットフォームでの認証用
      • olp-sdk-dataservice-read プラットフォームデータの読み取り用
      <script src="https://unpkg.com/@here/olp-sdk-authentication@1.2.1/bundle.umd.dev.js" charset="utf-8"></script>
      <script src="https://unpkg.com/@here/olp-sdk-dataservice-read@1.2.1/bundle.umd.dev.js" charset="utf-8"></script>
      
    • プラットフォームレイヤースキーマから Protobuf ファイルを取得するための JSZip ライブラリ、 protobuf.js および Protobuf でエンコードされたデータを GeoJSON にデコードするためのライブラリ :

      <script src="https://unpkg.com/jszip@3.2.2/dist/jszip.js" charset="utf-8"></script>
      <script src="//cdn.rawgit.com/dcodeIO/protobuf.js/6.8.4/dist/protobuf.min.js"></script>
      
  3. 次の場所に表示スクリプトを追加 <head>します。

    <script src="./your_script.js" charset="utf-8"></script>
    

    以下の章では、プラットフォームでの認証、レイヤーデータの取得、ベース マップでのデータの視覚化を行うために、対応するライブラリを実装する方法について詳しく説明します。

  4. Leaflet がサポートするマップ ( HERE ビジュアル化に最適化した地図 Plus を含む ) を配置する要素 <body> を次のセクションに追加します。

    <div id="map" style="height: 100%"></div>
    

プラットフォームでの認証

プラットフォームで認証するには、アクセス トークンを返す関数を使用する必要があります。 UserAuth コンストラクタで、アプリ資格情報アクセスキーの ID 、シークレット、およびプロジェクトのスコープを指定します ( 任意 ) 。

// Get a function, that will provide a token to access HERE data.
const token = new UserAuth({
    env,
    credentials: {
        accessKeyId,
        accessKeySecret
    },
    tokenRequester: requestToken,
    scope
}).getToken();
getToken = () => token;

これらの資格情報の入手方法については 、「資格情報を入手する」を参照してください。

プラットフォームデータを読み込んでいます

プラットフォームデータを取得するには、データを含むレイヤーのインスタンスが必要です。

/**
 * Fetch the layer config and return an instance of a layer client.
 *
 * @param hrn A catalog HRN.
 * @param layerId A layer ID.
 * @param settings Client settings.
 */
async function getLayerConfig(hrn, layerId, settings) {
    const catalogClient = new CatalogClient(HRN.fromString(hrn), settings);
    const config = await catalogClient.getCatalog(new CatalogRequest());
    return config.layers.find(item => item.id === layerId);
}

/**
 * Fetch the layer config and return an instance of a layer client.
 *
 * @param layerType A layer type.
 * @param hrn A catalog HRN.
 * @param layerId A layer ID.
 * @param settings Client settings.
 */
function getLayerClient(layerType, hrn, layerId, settings) {
    const hrnInstance = HRN.fromString(hrn);
    const layerClientParams = { catalogHrn: hrnInstance, layerId, settings };
    switch (layerType) {
        case "versioned":
            return new VersionedLayerClient(layerClientParams);

        case "volatile":
            return new VolatileLayerClient(layerClientParams);

        default:
            throw new Error(`Layer type "${layerType}" is not supported yet.`);
    }
}
// Get layer object, that will fetch GeoJSON data.
const settings = new OlpClientSettings({
    environment: env,
    getToken
});
const layerConfig = await getLayerConfig(hrn, layerId, settings);
if (!layerConfig) {
    throw new Error("Layer config was not found");
}

const layer = getLayerClient(layerConfig.layerType, hrn, layerId, settings);

レイヤーデータが Protobuf でエンコードされている場合は、エンコードされたデータを GeoJSON データに変換するデコーダーを提供する必要があります。 通常、デコーダーはレイヤーに関連付けられているスキーマに存在します。 そのため、スキーマを読み込んでそこからデコーダーを取得する必要があります。

/**
 * Fetch and process schema archive to prepare a Protobuf decoder.
 * 
 * @param layer Instance of a layer client.
 */
async function getDecoder(hrn, settings) {
    // Get schema with protobuf files
    const artifactClient = new ArtifactClient(settings);
    const detailsRequest = new SchemaDetailsRequest()
        .withSchema(HRN.fromString(hrn));
    const details = await artifactClient.getSchemaDetails(detailsRequest);

    if (details === undefined || details.variants === undefined) {
        return;
    }

    const variant = details.variants.find(item => item.id === "ds");
    if (variant === undefined) {
        return;
    }

    const request = new SchemaRequest().withVariant(variant);
    const archive = await artifactClient.getSchema(request);

    // Load schema as a ZIP archive
    const zip = new JSZip();
    await zip.loadAsync(archive);

    // Read all .proto file and parse them by Protobuf
    const protobufRoot = new protobuf.Root();
    Object.keys(zip.files).forEach(async fileName => {
        if (!fileName.endsWith(".proto")) {
            return;
        }

        const file = await zip.file(fileName).async("text");
        protobuf.parse(file, protobufRoot, { keepCase: true })
    });

    // Extract the manifest data.
    const manifestFile = await zip.file("META-INF/layer.manifest.json").async("text");
    const manifest = JSON.parse(manifestFile);

    return protobufRoot.lookupType(manifest.main.message);
}
if (layerConfig.schema === undefined || layerConfig.schema.hrn === undefined) {
    throw new Error("Layer schema HRN is not defined");
}

// Get a decoder from the schema.
const decoder = await getDecoder(layerConfig.schema.hrn, settings);
if (!decoder) {
    throw new Error("Decoder was not found.");
}

パーティションをビジュアル化してリーフレットに追加するように要求します。 データが GeoJSON 形式の場合は、 Leaflet geoJSON メソッドを使用してデータを視覚化します。

// Get tile data and add to Leaflet.
partitions.forEach(async partition => {
    const request = new DataRequest()
        .withPartitionId(`${partition}`);
    const response = await layer.getData(request);
    const data = await response.json();

    L.geoJSON(data)
        .bindPopup(item => item.feature.properties.tooltip)
        .addTo(map);
});

エンコードされたデータはまずデコードする必要があります。その後、データを GeoJSON に変換し、 LEaflet geoJSON のメソッドで表示できます。

// Fetch, decode and visualize specific partitions.
partitions.forEach(async partition => {
    const request = new DataRequest()
        .withPartitionId(`${partition}`);
    const response = await layer.getData(request);
    const data = await response.arrayBuffer();

    const decodedData = decode(data, decoder);

    const geojson = decodedData.segment.map(segment => ({
        type: "Feature",
        properties: {
            tooltip: segment.identifier
        },
        geometry: {
            type: "LineString",
            coordinates: segment.geometry.point.map(point => [point.longitude, point.latitude])
        }
    }));

    L.geoJSON(geojson)
        .bindPopup(layer => layer.feature.properties.tooltip)
        .addTo(map);
});

HERE ビジュアル化に最適化した地図 Plus ベース マップを表示します

以下のコード スニペットで harp.gl は、リーフレット用のプラグインを使用して HERE ビジュアル化に最適化した地図 Plus ベース マップを視覚化する方法を示します。

// Add the HERE base map. This can be replaced with the code of your preferred base map.
const harpLeaflet = new L.HarpGL({
    theme: "https://unpkg.com/@here/harp-map-theme@0.20.0/resources/berlin_tilezen_night_reduced.json"
}).addTo(map);
const baseMapLayerConfig = await getLayerConfig(baseMapHRN, "omv-plus-v2", settings);
if (!baseMapLayerConfig) {
    throw new Error("Base map layer was not found");
}
const baseMapLayer = getLayerClient(baseMapLayerConfig.layerType, baseMapHRN, "omv-plus-v2", settings);
harpLeaflet.mapView.addDataSource(new harp.OmvDataSource({
    dataProvider: {
        async getTile(tileKey) {
            const request = new DataRequest()
                .withPartitionId(`${mortonCodeFromQuadKey(tileKey)}`);
            const response = await baseMapLayer.getData(request);
            return response.arrayBuffer();
        },
        async connect() { },
        async ready() { return true; },
        async register() { },
        async unregister() { },
    },
    layerName: "omv-plus-v2",
    getBearerToken: getToken,
    styleSetName: "tilezen"
}));

// add HERE copyright notice
const year = new Date().getFullYear();
const HERECopyright = (env === "here-cn") ? "HERE - GS(2020)7042" : "HERE"
map.attributionControl.addAttribution(`&copy; <a href="https://legal.here.com/terms">${year}` +
    ` ${HERECopyright}</a>`);

」に一致する結果は 件です

    」に一致する結果はありません