Vue.jsでしょぼいメニューを作った

さいきんVue.js大好きおじさんになりつつあるのだけれども、メニューっぽいものを実装するところで詰まった。jQueryだとメニュー関係のプラグインが豊富にあるのでテキトーやっててもよかったのだが、Vue.jsだとよくわかんない感じ。

小一時間WEBの海を泳いでかっこいいメニューのサンプルを見つけても、「どれどれ」とソースコード眺めてみたらハイレベルすぎて俺みたいなクソザコナメクジには到底理解できないことが分かった。うーん、こりゃ困ったぜ。

といったところで、とりあえず車輪探しは諦めて、自分でサクッと作ってみる事にした。そして手を動かした結果、「すまん・・・俺の実力ではこれが限界だ・・・!」と胸を張って謝れる程度のしょぼいメニューが出来上がったので、ここに残しておこうと思う。

ひとまずJSFiddleをペタペタ。

今回は、下記の挙動をすればオッケーという仕様にした。
・メニューは「メイン項目」と「サブ項目」で構成されている。
・メイン項目やサブ項目は、マウスカーソルがホバーしたらハイライト表示する。
・サブ項目をクリックしたら、任意のメソッドを実行する。

  created : function(){
  	// メインメニューとサブメニュー
  	this.list_item.push({
    		main : "ラピュタ",
    		sub : [
      			// メニュー名と実行される処理のセット
      			{ name : "パズー",	proc : this.laputa },
        		{ name : "シータ",	proc : this.laputa },
        		{ name : "ムスカ",	proc : this.laputa },
    		]
 	});

メニューは、こんな感じでlist_itemに追加していく。subのprocには、サブメニューがクリックされたときに実行させたい処理をテキトーにぶちこんでおく。

new Vue({
	el : "#menu",
  	data : {
  		// メニューアイテム
  		list_item : [],
    		// ホバー中アイテム
    		is_hover : {
    			main : null,
      			sub : null,
    		}
  	},

次にデータの定義。list_itemがメニューをぶちこむ配列。で、ホバー中の項目をどうやってデータに持たせるかというのを試行錯誤したのだが、is_hoverとかいうのを作って、そいつにホバー中のメニューへの参照をぶちこむことにした。このあたりたぶんもっとうまいやり方があると思うのだが・・・

  <li class="main" v-for="item in list_item" @mousemove="main_enter(item)" @mouseleave="main_leave">
    <div :class="{'hover-main':(is_hover.main == item)}">
      {{item.main}}
    </div> 

追加したメニューのデータに対して、表示側ではv-forでぶんまわしながら表示。マウスがフォーカスしてるときはホバー中の表示にしたいので、mousemoveとmouseleaveイベントにそれ用の処理を設定。ハイライト表示への切り替えは、「is_hover.mainに入ってるオブジェクトにhover-mainを適用しまっせ」的な感じにしておいた。

  methods : {  
  	// マウスカーソル入ったとき
  	main_enter : function(item){
    		this.is_hover.main = item;
    	},
	    // マウスカーソル外れたとき
    	main_leave : function(){
    		this.is_hover.main = null;
    	},

Javascript側ではこう。

<ul class="sub" v-if="is_hover.main == item"> 
  <li :class="{'hover-sub':(is_hover.sub == subitem)}" v-for="subitem in item.sub" @mousemove="sub_enter(subitem)" @mouseleave="sub_leave" @click="clicked(subitem)">{{subitem.name}}</li>
</ul>

サブメニューも、メインメニューとやってることは基本的に同じ。違うところとしては、クリックイベントを持たせてる所ぐらいか。

    // クリック時の処理
    clicked : function(subitem){
    	subitem.proc(subitem);
    }

クリックイベントの裏でやってることは、サブメニューのデータを追加するときに指定したメソッドを引数つけて愚直に呼び出してるだけ。

まあ、見た目はともかくとして当初予定してた実装はできたので、今年中にお仕事終わらせて年始のジブリ祭りに備えないとやね。ユパ様好き好き。だが聖司は許さん爆発しろ。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

日本語が含まれない投稿は無視されますのでご注意ください。(スパム対策)