☀️

天気情報を表示するウェブコンポーネント

2024/11/27に公開

1日の天気情報を表示するためのウィジェットを作成するウェブコンポーネントを作りました。

詳細なAPIに関しては、Weather widgetのリポジトリをご確認ください。


基本的な使い方

はじめに、コンポーネントはこのようなデータを受け取ることを前提としています(ただし独自の変換器も利用できます)。

{
  "date": "2024-11-20T00:00:00.000Z",
  "location": "東京都",
  "main": {
    "weather": "晴れ",
    "temp": 22.5,
    "pop": 0.1
  },
  "hours": [
    {
      "time": "2024-11-20T00:00:00.000Z",
      "weather": "曇り",
      "temp": 18.2,
      "pop": 0.2
    },
    {
      "time": "2024-11-20T03:00:00.000Z",
      "weather": "曇り",
      "temp": 17.8,
      "pop": 0.3
    },
    {
      "time": "2024-11-20T06:00:00.000Z",
      "weather": "雨",
      "temp": 16.5,
      "pop": 0.7
    },
    {
      "time": "2024-11-20T09:00:00.000Z",
      "weather": "雨",
      "temp": 20.0,
      "pop": 0.1
    },
    {
      "time": "2024-11-20T12:00:00.000Z",
      "weather": "晴れ",
      "temp": 22.5,
      "pop": 0.05
    },
    {
      "time": "2024-11-20T15:00:00.000Z",
      "weather": "晴れ",
      "temp": 23.0,
      "pop": 0
    },
    {
      "time": "2024-11-20T18:00:00.000Z",
      "weather": "曇り",
      "temp": 21.2,
      "pop": 0.1
    },
    {
      "time": "2024-11-20T21:00:00.000Z",
      "weather": "雪",
      "temp": 19.0,
      "pop": 0.2
    },
    {
      "time": "2024-11-21T00:00:00.000Z",
      "weather": "曇り",
      "temp": 19.0,
      "pop": 0.2
    }
  ]
}
  1. パッケージをインストールします。

    npm i @kokomin/weather-widget
    
  2. マークアップを記述します。

    <body>
        <weather-widget></weather-widdget>
        <script src="./index.js"></script>
    </body>
    
  3. スクリプトを書きます。

    const weather_widget = document.querySelector("weather-wiget");
    
    // APIエンドポイントから天気情報を取得したり、そのままデータを割り当てても構いません。
    fetch("API_ENDPOINT")
        .then(res => res.json())
        .then(data => weather_widget.data = data);
    
  4. UIは一通り完成します

天気ウィジェットのメイン画面。真ん中には晴れを表す大きな太陽の画像があり、取得した天気情報の場所、日付、主要な天気に関する情報が表示されている。

天気ウィジェットのチャート画面。1日の天気の気温変化を1時間ごとに表す折れ線グラフと詳細な天気情報を表すテーブルがある。

天気ウィジェットの検索画面。デフォルトで、現在地や郵便番号、地域名から検索できるフォームになっている。

『現在地を取得する』ボタンを押すと、Geolocation APIにより、ユーザーの緯度・経度を取得できます。郵便番号の入力フォームは検証されエラーメッセージを表示するようにしているため、改めて検証を行う必要はありません。

weather-widgetの検索ダイアログの郵便番号が検証されている様子。

地域名の検索候補はarea-suggesions属性またはarea_suggestionsプロパティに値をセットすることで、機能します。属性として渡す場合にはJSON形式の文字列である必要があります。

inputEl.setCustomValidity()inputEl.reportValidity()といったWeb APIで実現されています。クールですよね?

また、ユーザーが地域名を入力しやすいよう提案を表示することも可能です。

<weather-widget area-suggestions='["北海道", "青森県", "秋田県"]'></weather-widget>

weather-widgetの検索ダイアログで検索候補地が示されている様子。

これはHTMLの<datalist>要素で実現されています。

この検索ダイアログは<dialog>要素で構成されているため、position: absolute;を使ったときのように、タブキーでダイアログ外のタブキー移動が起こらず(不活性化されている)アクセシビリティにも優れています。

イベント

デフォルトでは、現在地、郵便番号、地域名から検索できるフォームになっています。

searchイベントから、これらのフォームから送信されたデータを取得できます。

weather_widgets.addEventListener('search', (event) => {
  const detail = event.detail;

  switch (detail.method) {
    case 'zipcode':
      console.log('郵便番号', detail.zipcode);
      break;
    case 'area':
      console.log('ユーザーが入力した地域名', detail.area);
      break;
    case 'location':
      const location = detail.location;

      if (!location) {
        console.error('ユーザーが現在地の取得を拒否しました。');
        return;
      }

      console.log('ユーザーがいる場所の緯度', location.latitude);
      console.log('ユーザーがいる場所の経度', location.longitude);
      break;
  }
});

テーマの切り替え

テーマの切り替えは、基本的にCSS一行で済むよう設計されています。詳細はリポジトリを確認してください。カスタマイズ可能な、いくつかのCSSパーツとCSS変数が用意されています。

:root {
    --weather-widget-theme-hue: 30;
}

赤色にテーマを変更した天気ウィジェット

ご覧いただきありがとうございました。

Discussion