ボタンをクリックしたら、別の要素内にあるリストのstyleを変える方法[JavaScript]

ボタンをクリックしたら、別の要素内にあるリストのstyleを変える方法[JavaScript]
今回は、以前書いた
クリックされた要素を特定してdata属性から情報を取得する方法
という記事に似た内容です。
上記の記事では、「クリックされた要素を特定してdata属性から情報を取得」という、ただその点にだけ焦点を当てています。
今回は、その取得したdata属性を使って「異なる要素内にあるリストの見た目を変える」という事について書いていきます。

例えば、
左側にボタン、右側にリストがあるUIがあったと仮定します。
左側のボタンを押すと、それに対応する
右側のリストが選択状態になる。

そんなUIを作りたい場合に応用できる、素のJavaScriptを使った(≒jQueryではない)基本的な方法についての記事です。

↑このように、それぞれ別の位置にある、別の要素に内包された要素を連動させる方法についての記事です。左に並ぶボタンをクリックすると、対応する右側のリストが反応していることがわかります。サンプルなので見た目はごくごくシンプルですが、この仕組みを覚えておくと、タブ型のUIを作る際などにも応用が効くかと思います。

まずは結論から

次のようなUIがあったとします。(サンプルなので、見た目はものすごくシンプルです)

[html]

<div class="my-wrapper">
  <div class="my-item-left">
    <button class="my-button" data-button="targetA">要素A</button>
    <button class="my-button" data-button="targetB">要素B</button>
    <button class="my-button" data-button="targetC">要素C</button>
    <button class="my-button" data-button="targetD">要素D</button>
    <button class="my-button" data-button="targetE">要素E</button>
  </div>
  <div class="my-item-right">
    <ul class="my-list">
      <li class="my-list-item" data-list="targetA">リスト項目A</li>
      <li class="my-list-item" data-list="targetB">リスト項目B</li>
      <li class="my-list-item" data-list="targetC">リスト項目C</li>
      <li class="my-list-item" data-list="targetD">リスト項目D</li>
      <li class="my-list-item" data-list="targetE">リスト項目E</li>
    </ul>
  </div>
</div>

↑冒頭で書いた通り、
「左側にボタン、右側にリスト」がある状態のhtmlになります。
html側でのポイントは、ボタン側・リスト側それぞれに「同じ値を持ったカスタムdata属性」を定義しておく点です。
※後述しますが、もちろん一致させられればclass名でも良いですし、id名とdata属性のペアでも大丈夫です。
これに、簡単にstyleを用意しておきます。

[css]

.my-wrapper {
  display: flex;
  justify-content: center;
  padding: 2rem;
  width: 1200px;
}
.my-item-left {
  display: flex;
  flex-direction: column;
  justify-content: center;
  margin: 0 2rem 0 0;
}
.my-button {
  align-items: center;
  background: #ebebeb;
  border: none;
  border-radius: 9999px;
  cursor: pointer;
  display: flex;
  font-size: .875rem;
  height: 48px;
  justify-content: center;
  margin: 0 0 1rem 0;
  width: 160px;
}
.my-list {
  box-shadow: 0px 1px 3px rgba(0, 0, 0, .3);
  list-style-type: none;
  margin: 0;
  padding: 0;
}
.my-list-item {
  border-bottom: 1px solid #ebebeb;
  font-size: .875rem;
  min-width: 360px;
  padding: 1rem 2rem; 
  transition: background-color .3s, color .3s, font-weight .3s;
}
.my-list-item.is-selected {
  background: #beb9b9;
  color: #fff;
  font-weight: 700;
}

↑何度も言いますがサンプルなので、ものすごく簡素な見た目になります。
ここで定義したcssの中で、次のセクションで書く
JavaScript内で使用することになるのは
.my-list-item.is-selected
の部分で、この .is-selected が付与されると、リスト側の見た目が変化する仕組みです。

左側のボタンを押すと、対応する右側のリストが反応する仕組み

上記のコードで、ものすごくシンプルながら
「左側にボタン、右側にリスト」があるUIの準備ができました。

それではここに、
「左側のボタンを押す」と、
「それに対応する右側のリストが選択状態になる」
という仕組みを、素のJavaScriptで(≒jQuery非依存で)記述します。

[JavaScript]

<script>
  const myClickButtons = document.querySelector('.my-item-left');
  const myClickLists = document.querySelectorAll('.my-list-item');
  myClickButtons.addEventListener('click', (e)=> {
    // listのclassを初期化
    myClickLists.forEach((list)=>{
      list.classList.remove('is-selected');
    });
    const dataButton = e.target.getAttribute('data-button');
    if(dataButton !== null) {
      const myListItem = document.querySelector('.my-list-item[data-list="'+dataButton+'"]');
      myListItem.classList.add('is-selected');
    } else {
      return;
    };
  });
</script>

JavaScript部分について

上で書いた JavaScript の仕組みは至ってシンプルです。
まず、
2行目、3行目では対象となる要素を取得しています。
2行目が、ボタン要素を包括する親要素。
3行目が、ボタンを押したら変化をつけたいリスト達です。
4行目〜末尾までが、2行目で定義したボタンをクリックした際に実行される関数です。
4行目では、 addEventListener('click', アロー関数... の形で、
clickイベントが発生した場合を監視しています。
(e)=> {...(中略)
↑このように書いておくと、(ものすごくざっくり言うと)
e にはclickイベントが発生した箇所の内容が入ってくるので、
9行目にあるように、
const dataButton = e.target.getAttribute('data-button');
として、クリックされたボタンが持っているdata属性 ‘data-button’ の値が取得できるわけです。
10行目〜末尾は、リストにclassを付与して、押されたボタンの条件にあてはまるリストを更新している部分になります。
ポイントは、あらかじめ
ボタン側にもリスト側にも、一致する値を持たせたdata属性を定義しておく点です。(この例の場合、data-button と data-list)
※もちろんdata属性でなくとも、識別できるclass名などでも大丈夫です。
id名だと同一ページで同名idが重複してしまい、htmlのお作法的に非推奨となるので、つけるなら片方をidにしてもう一方を何らかの値(リンクを持っている場合はアンカーの値などでも可)で一致させる形がとれれば何をトリガーにしても大丈夫です。

そして
10行目〜末尾の内容ですが、
const myListItem = document.querySelector('.my-list-item[data-list="'+dataButton+'"]');
として、9行目で取得したボタンのdata属性に一致するリストを取得。
data属性の値が一致したリスト項目に対して、 is-selected というclassを付与しています。
この時、関連してくるのが 5〜8行目 に書いてある部分で、
5〜8行目であらかじめ、リスト(3行目で一括取得している)に対して、初期化をおこなっている点です。
具体的には、ボタンがクリックされるたび is-selected というclassを全てのリストから外しています。
これをしておくことで、クリックするたびに対応するリストのみ、見た目が更新されている様に見せているという事です。

とても基本的な形ですが、以上の html, css, JavaScript で
左側のボタンを押す」と、
それに対応する右側のリストが選択状態になる」
という仕組みを、素のJavaScriptで(≒jQuery非依存で)つくることができます。

この記事のまとめ

今回は、たいへんシンプルながら、
「左側のボタンを押すと、それに対応する右側のリストが選択状態になる」

そんなUIを作りたい場合に応用できる、素のJavaScriptを使った(≒jQueryではない)基本的な方法についての記事を書きました。

一見くだらないようでいて、この基本的な仕組みを知っておくと、
素のJavaScriptを使った見た目の操作でよく使う

・querySelector
・querySelectorAll
・classList.add / classList.remove
・addEventListener

↑このあたりに慣れる事ができるので、脱jQueryを目指すWebデザイナーの方などにとっては
役に立つかもしれません。

この記事が皆さんのより良いWeb制作体験につながれば、嬉しく思います。

※この記事は内容の品質向上を目的に、随時更新を行う場合があります。

この記事をシェアする: