Svelte와 방해석 소개

웹 컴포넌트



일정 시간 동안 웹 앱을 구축해 왔다면 아마도 Web Components 을 접했을 것입니다. 웹 컴포넌트는 많은 것을 제공합니다. 사용하는 프레임워크에 관계없이 어디서나 사용할 수 있는 일련의 공통 구성 요소를 구축할 수 있습니다. 이에 대해 자세히 설명하지는 않겠지만 자신의 응용 프로그램에서 Calcite Components과 같은 웹 구성 요소 라이브러리를 사용할 수 있다는 점을 강조하고 싶습니다. 오늘날 일부 프레임워크에서는 다른 프레임워크보다 웹 구성 요소를 사용하는 것이 더 쉽습니다. 가장 친근한 것 중 하나는 Svelte 입니다.

이 게시물에서는 this Calcite Components tutorial을 따라 매핑 앱을 빌드하지만 Svelte!

The source code for the demo in this blog post is on github.



시작하기



Esri blog에서 ArcGIS API for JavaScript와 함께 Svelte를 사용하는 방법에 대한 훌륭한 소개를 읽을 수 있습니다.

Vite 을 사용하여 Svelte 앱 구축을 시작할 수 있습니다. 예, 저는 요즘 거의 모든 작업에 Vite를 사용합니다.

npm init @vitejs/app svelte-calcite
cd svelte-calcite
npm install @arcgis/core


일단 설치되면 ArcGIS API for JavaScript을 설치할 수 있습니다. 방해석 구성 요소 라이브러리가 함께 설치됩니다. 이 시점에서 scaffold 응용 프로그램의 css 및 .svelte 파일을 비울 수 있습니다. 시작할 기본 CSS를 추가할 수 있습니다.

/** app.css **/
@import "https://js.arcgis.com/calcite-components/1.0.0-beta.86/calcite.css";
@import "https://js.arcgis.com/4.24/esri/themes/light/main.css";

html,
body,
#app {
  padding: 0;
  margin: 0;
  height: 100%;
  width: 100%;
}


매핑 앱 만들기



그런 다음 매핑 자습서에 따라 App.svelte 구성 요소 업데이트를 시작할 수 있습니다. 앱의 HTML 뼈대로 시작할 수 있습니다.

<calcite-shell content-behind>
    <h2 id="header-title" slot="header">
    <!-- Dynamically populated -->
    </h2>
    <calcite-shell-panel slot="primary-panel" detached>
    </calcite-shell-panel>
    <div class="viewDiv"></div>
</calcite-shell>


이것은 앱의 기본 셸을 제공하지만 지도를 표시하려면 여전히 이것을 다른 부분에 연결해야 합니다.

<script>
  // calcite components
  import "@esri/calcite-components/dist/components/calcite-shell";
  import "@esri/calcite-components/dist/components/calcite-shell-panel";

  // arcgis js api
  import config from "@arcgis/core/config";
  import WebMap from "@arcgis/core/WebMap";
  import MapView from "@arcgis/core/views/MapView";

  import { onMount } from "svelte";

  config.apiKey = import.meta.env.VITE_API_KEY;

  let viewContainer;

  let item = {};

  onMount(() => {
    const map = new WebMap({
      portalItem: {
        id: "cc3bd744b9a44feaa493dd867a1d48dd",
      },
    });
    const view = new MapView({
      container: viewContainer,
      map,
      padding: {
        left: 49,
      },
    });

    view.ui.move("zoom", "bottom-right");

    map.when(() => {
      item = map.portalItem;
    });
  });
</script>


시작하기 위해 여기에서 몇 가지 작업을 수행하고 있습니다. 먼저 지금까지 앱에서 사용하고 있는 Calcite 구성 요소에서 모듈을 가져옵니다. 그렇지 않으면 맞춤 요소로 등록되지 않고 표시되지 않습니다. 그런 다음 페이지에서 참조할 수 있는 몇 가지 변수를 정의합니다. Svelte는 변수 및 making them reactive을 바인딩하는 매우 명확한 방법을 가지고 있습니다. 이것은 다른 프레임워크에서 오는 신선한 공기의 숨결입니다. viewContainer는 지도를 표시할 수 있는 요소에 대한 참조로 사용되며 item 객체는 일부 텍스트를 표시하기 위해 참조할 수 있습니다.

<calcite-shell content-behind>
    <h2 id="header-title" slot="header">
    {item.title || "...loading"}
    </h2>
    <calcite-shell-panel slot="primary-panel" detached>
    </calcite-shell-panel>
    <div class="viewDiv" bind:this={viewContainer} />
</calcite-shell>

item.title를 참조하고 해당 변수를 업데이트하면 페이지에 반영됩니다. bind:this 구문을 사용하여 viewContainer 변수를 div 요소에 바인딩합니다. thisbind: 구문을 사용 중인 요소를 나타냅니다. 나는 그 API를 정말로 파헤친다.

자습서의 다음 단계는 위젯이 이동하는 작업 표시줄과 패널을 설정하는 것입니다.

<calcite-shell content-behind>
  <h2 id="header-title" slot="header">
    {item.title || "...loading"}
  </h2>
  <calcite-shell-panel slot="primary-panel" detached>
    <calcite-action-bar slot="action-bar">
      <calcite-action data-action-id="layers" icon="layers" text="Layers" />
      <calcite-action
        data-action-id="basemaps"
        icon="basemap"
        text="Basemaps"
      />
      <calcite-action data-action-id="legend" icon="legend" text="Legend" />
      <calcite-action
        data-action-id="bookmarks"
        icon="bookmark"
        text="Bookmarks"
      />
      <calcite-action data-action-id="print" icon="print" text="Print" />
      <calcite-action
        data-action-id="information"
        icon="information"
        text="Information"
      />
    </calcite-action-bar>

    <calcite-panel
      heading="Layers"
      height-scale="l"
      data-panel-id="layers"
      hidden
    >
      <div id="layers-container" bind:this={layerListContainer} />
    </calcite-panel>
    <calcite-panel
      heading="Basemaps"
      height-scale="l"
      data-panel-id="basemaps"
      hidden
    >
      <div id="basemaps-container" bind:this={bmgContainer} />
    </calcite-panel>
    <calcite-panel
      heading="Legend"
      height-scale="l"
      data-panel-id="legend"
      hidden
    >
      <div id="legend-container" bind:this={legendContainer} />
    </calcite-panel>
    <calcite-panel
      heading="Bookmarks"
      height-scale="l"
      data-panel-id="bookmarks"
      hidden
    >
      <div id="bookmarks-container" bind:this={bookmarksContainer} />
    </calcite-panel>
    <calcite-panel
      heading="Print"
      height-scale="l"
      data-panel-id="print"
      hidden
    >
      <div id="print-container" bind:this={printContainer} />
    </calcite-panel>
    <!-- Info panel (populates with info from the web map) -->
    <calcite-panel heading="Details" data-panel-id="information" hidden>
      <div id="info-content">
        <img
          id="item-thumbnail"
          alt="webmap thumbnail"
          src={item.thumbnailUrl}
        />
        <div id="item-description">
          <!-- Dynamically populated -->
          {item.description}
        </div>
        <calcite-label layout="inline">
          <b>Rating:</b>
          <calcite-rating id="item-rating" read-only>
            <!-- Dynamically populated -->
            {item.avgRating}
          </calcite-rating>
        </calcite-label>
      </div>
    </calcite-panel>
  </calcite-shell-panel>
  <div class="viewDiv" bind:this={viewContainer} />
</calcite-shell>


좋아, 우리는 지금 많이 추가했습니다. 버튼을 추가하고 일부 위젯의 가시성을 전환할 수 있는 구성 요소와 action bar이 더 있습니다. 이전에 사용한 것과 동일한bind:this 구문을 사용하고 있습니다. 더 많은 구성 요소를 추가했으므로 더 많은 모듈을 가져와야 하며 위젯 초기화를 시작할 수 있습니다.

<script>
  // calcite components
  import "@esri/calcite-components/dist/components/calcite-shell";
  import "@esri/calcite-components/dist/components/calcite-shell-panel";
  import "@esri/calcite-components/dist/components/calcite-action";
  import "@esri/calcite-components/dist/components/calcite-action-bar";
  import "@esri/calcite-components/dist/components/calcite-panel";
  import "@esri/calcite-components/dist/components/calcite-label";
  import "@esri/calcite-components/dist/components/calcite-rating";

  // arcgis js api
  import config from "@arcgis/core/config";
  import WebMap from "@arcgis/core/WebMap";
  import MapView from "@arcgis/core/views/MapView";
  import Bookmarks from "@arcgis/core/widgets/Bookmarks";
  import BasemapGallery from "@arcgis/core/widgets/BasemapGallery";
  import LayerList from "@arcgis/core/widgets/LayerList";
  import Legend from "@arcgis/core/widgets/Legend";
  import Print from "@arcgis/core/widgets/Print";
  import { onMount } from "svelte";

  config.apiKey = import.meta.env.VITE_API_KEY;

  let viewContainer;

  let bookmarksContainer;
  let bmgContainer;
  let layerListContainer;
  let legendContainer;
  let printContainer;

  let item = {};

  onMount(() => {
    const map = new WebMap({
      portalItem: {
        id: "cc3bd744b9a44feaa493dd867a1d48dd",
      },
    });
    const view = new MapView({
      container: viewContainer,
      map,
      padding: {
        left: 49,
      },
    });

    view.ui.move("zoom", "bottom-right");

    const basemaps = new BasemapGallery({
      view,
      container: bmgContainer,
    });
    const bookmarks = new Bookmarks({
      view,
      container: bookmarksContainer,
    });
    const layerList = new LayerList({
      view,
      selectionEnabled: true,
      container: layerListContainer,
    });
    const legend = new Legend({
      view,
      container: legendContainer,
    });
    const print = new Print({
      view,
      container: printContainer,
    });

    map.when(() => {
      item = map.portalItem;
    });
  });
</script>


이 시점에서 우리의 애플리케이션은 거의 완성되었습니다. 아직 위젯을 전환할 수 있는 방법이 없다는 점만 제외하면 말입니다. 매핑 자습서에는 있는 그대로 재사용할 수 있는 이 코드 구문이 있습니다.

let activeWidget;

const handleActionBarClick = ({ target }) => {
if (target.tagName !== "CALCITE-ACTION") {
    return;
}

if (activeWidget) {
    document.querySelector(`[data-action-id=${activeWidget}]`).active = false;
    document.querySelector(`[data-panel-id=${activeWidget}]`).hidden = true;
}

const nextWidget = target.dataset.actionId;
if (nextWidget !== activeWidget) {
    document.querySelector(`[data-action-id=${nextWidget}]`).active = true;
    document.querySelector(`[data-panel-id=${nextWidget}]`).hidden = false;
    activeWidget = nextWidget;
} else {
    activeWidget = null;
}
};


액션 바에 이벤트 리스너를 추가하기만 하면 됩니다.

<calcite-action-bar slot="action-bar" on:click={handleActionBarClick}>
...
</calcite-action-bar>


on:eventname 구문은 Svelte에서 이벤트 리스너를 추가하는 방법입니다.

이제 애플리케이션이 완료되었으며 지도를 보고 위젯을 전환할 수 있습니다.

요약



저는 Svelte 고급 사용자는 아니지만 빠르게 성장하고 있습니다. 내가 좋아하는 웹 구성 요소를 더 쉽게 사용할 수 있는 모든 프레임워크. Calcite Components는 ArcGIS Platform 앱을 구축하기 위한 훌륭한 웹 구성 요소 라이브러리이기도 합니다.

자세한 내용은 이 비디오를 시청하세요!

좋은 웹페이지 즐겨찾기