JavaScript で作る言語スイッチャー(リスト表示編)

多言語サイトにおける汎用的な言語スイッチャー(各言語間で対応するページにリンクする機能)を JavaScript で作ってみました。a-blog cms 以外の CMS で制作したサイトや静的なサイトでもドキュメントルートの次が言語のスラッグになっていて、それ以外のパスは全言語で共通という場合には使えるのでぜひ参考にしたり、用途に合わせてカスタマイズしたりしてみてください。

a-blog cms の場合はエイリアスで制作した多言語サイトの場合にこの条件を満たしているので使えます。ここでは HTML ソースとして日英中の3言語の場合を例に書きますが、JavaScript の方は何種類の言語があってもそのままで対応できます。


HTML

今回はリスト表示編なので、HTML側ではリストのソースを用意します。

<ul class="js-lang-switch-list">
  <li data-slug="">日本語</li>
  <li data-slug="en">English</li>
  <li data-slug="zh-CN">中文</li>
</ul>

UL要素に js-lang-switch-list という class を振り、LI要素には data-slug 属性としてぞれぞれの言語のスラッグを入れてください。このスラッグが、url で使われているスラッグと一致しているようにしてください。ベースとなる言語(ここでは日本語)の data-slug は空にしておいてください。

JavaScript

DOMContentLoaded のタイミングで実行される場所に次の内容を追加してください。

// 言語スイッチャー
const langSwitchItems = document.querySelectorAll('.js-lang-switch-list > li');
// langSwitchItems のdata属性から配列を作る
const langArry = [];
langSwitchItems.forEach((element) => {
  const { slug } = element.dataset;
  if (langArry.indexOf(slug) === -1 && slug !== '') {
    langArry.push(slug);
  }
});
// 現在の pathname からベースになる(日本語の)pathname を取得する
const currentPathname = window.location.pathname;
const currentPathnameStrArry = currentPathname.split('/');
let basePathname = '';
// currentPathnameStrArry[1]がlangArryになければ日本語、そうでなければ日本語以外
if (langArry.includes(currentPathnameStrArry[1])) {
  // 日本語以外のサイトにいる場合
  basePathname = currentPathname.slice(currentPathnameStrArry[1].length + 1);
} else {
  // 日本語サイトにいる場合
  basePathname = currentPathname;
}
// langSwitchItems にリンクを設定する
langSwitchItems.forEach((element) => {
  const langSwitchItem = element;
  const link = document.createElement('a');
  link.innerHTML = langSwitchItem.innerHTML;
  if (langSwitchItem.dataset.slug === '') {
    // 日本語へのリンクの場合
    if (basePathname !== currentPathname) {
      // 日本語以外のサイトにいるときにはリンクを追加
      link.setAttribute('href', basePathname);
      langSwitchItem.innerHTML = '';
      langSwitchItem.append(link);
    }
  } else if (langSwitchItem.dataset.slug !== currentPathnameStrArry[1]) {
    // langSwitchItem.dataset.slug と currentPathnameStrArry[1] が一致しないときはリンクを追加
    link.setAttribute('href', `/${langSwitchItem.dataset.slug}${basePathname}`);
    langSwitchItem.innerHTML = '';
    langSwitchItem.append(link);
  }
});

1-2行目で .js-lang-switch-list の直下の LI要素を取得して、

3-10行目でその data-slug属性から重複と空の場合を除き、配列を作成しています。この配列の内容は、今回の場合は en と zh-CN になります。

11-22行目で、ベースになる(日本語の)pathname を basePathname として取得しています。日本語以外のサイトにいる場合は 言語スラッグ+/ を取り除き、日本語のサイトにいる場合は現在の pathname が basePathname になります。

23-42行目で、それぞれの LI要素に対して、別の言語のサイトにいる場合にのみリンクを追加しています。

JavaScript 実行後のソース

たとえば日本語のサイトにいる場合には


<ul class="js-lang-switch-list">
  <li data-slug="">日本語</li>
  <li data-slug="en"><a href="/en/......">English</a></li>
  <li data-slug="zh-CN"><a href="/zh-CN/......">中文</a></li>
</ul>

のようになり、English、中文のLI要素には対応するページへのリンクが追加されています。

後はCSSで自由にスタイリングしてください。

少しカスタマイズすればセレクトメニューの言語スイッチャーなども作れると思います。


この記事をシェアする

この記事を書いた人

有限会社 アップルップル

笠谷 亜貴子

このブログでは a-blog cms の実装に関することを中心に、CSS、JavaScriptなどフロントエンド周辺のことを書いていきます。

おすすめ記事

この記事のハッシュタグ から関連する記事を表示しています。

タグ一覧