JavaScriptとlistでコンボボックスを使ったタグ追加/削除機能を実装
WordPressの投稿画面とか、あるいは動画投稿サイトなどでもそうですが、最近は何かというとタグ付けが多いですよね。
カテゴリでガチガチに縛るよりも、柔軟に対応できるので良いと思うのですが、あんな機能を自分で作ったWebサイトにも付けるとしたら、どうやって実装するか、ちょっと考えてみました。
あ、データ構造とかそういう話ではなく、UI上のお話です。
オートコンプリートのリストを使ってタグ追加を実装してみる
まずは動きを見たほうが早いと思うので、さっそくですがサンプルです。
テキストボックスにカーソルを置くとタグの候補リスト(プログラミングとかJavaScriptとかPHPとか)が表示されるので、テキトーに選んで[追加]ボタンを押すと下にチェックボックス付きでタグが追加されます。
もちろん複数追加しても良いし、好きな単語を入力して追加してもOKです。また、チェックボックスのチェックを外すと追加されたタグは消えます。
Webブラウザ上で動いているだけで何かデータを送信したりとかはしないので安心してお試しくださいw
ソースコード
<input type="text" id="tag" list="taglist" placeholder="タグを入力" style="width:15em;">
<button id="addTag">追加</button>
<div id="div_tags"></div>
<datalist id="taglist">
<option value="プログラミング"></option>
<option value="PHP"></option>
<option value="JavaScript"></option>
<option value="CSS"></option>
</datalist>
<script>
document.getElementById('addTag').onclick = function () {
let text = document.getElementById('tag').value;
if (text.trim() == '') return;
//ラベルとチェックボックス要素を生成
let label = document.createElement('label');
let cb = document.createElement('input');
cb.type = 'checkbox';
cb.name = 'tags[]';
cb.value = text;
cb.checked = true;
cb.onclick = function () {
//チェックボックスがクリックされたらラベルごと消す
document.getElementById('div_tags').removeChild(label);
};
label.appendChild(cb); //ラベルの下にチェックボックス追加
let txt = document.createTextNode(text); //テキストノードを生成
label.appendChild(txt); //ラベルの下にテキストノードを追加
document.getElementById('div_tags').appendChild(label);
document.getElementById('tag').value = '';
};
</script>
意外とシンプルなコードだと思いますが、どうでしょう(自画自賛)
解説
テキストボックスにフォーカスをあてたときに出てくるコンボボックスみたいなものはブラウザの機能です。
inputタグにlist属性を付けて、taglistを指定してあげることで、入力候補を自動的に表示してくれます。すごく便利。
PHPと組み合わせれば「よく使うタグの一覧」みたいなのも簡単に実装できそうですね。
キモの部分はonclick以降のところですが、要するにlabelタグとcheckboxタグを自動生成しているだけです。
checkboxだとちょっとダサいのでspanタグとアイコンを組み合わせてかっちょ良くすることも考えたのですが、それだとコード長くてわかりづらくなりそうだったので、まずは見やすさ優先で作ってみました。
また、checkboxだと↓このように
<input type="checkbox" name="tags[]">
name属性に配列を指定することで、PHP等で受け取るのが楽になるかなという考えもあります。
まぁこのへんはtype=hidden付けたinputタグをどこかに仕込んでおいても良いんですけどね。お好み次第で。
まとめ
- WordPressの投稿画面にあるようなタグを追加したり削除したりするUIを作ってみたくなった。
- inputタグのlist属性を使うことでコンボボックスによるタグの入力とリストからの選択の両立は簡単に出来た。
- 追加ボタン押下時にlabelタグとcheckboxタグを生成することで、タグの追加が出来た。
- チェックボックスのonclickイベント時に親のlabelごと削除することでタグの削除も簡単に出来た。
ということで、見た目はあまりかっちょ良くないかもですが、やりたいことは出来た感じです。
大したコードではございませんが、お役に立つようでしたらご自由にお使いくださいませ。