【Vue.js】Routerでルーティングする

Routerとは、Vueが用意しているプラグインで、URLとプロジェクトを関連付ける役割をするもの。
これによって大規模SPAなどが作れる。

スポンサーリンク

Routerプラグインのセットアップ

CLIで、下記のコマンドを実行してRouterプラグインをインストール。

npm install vue-router

src直下にJSファイルを作成。良く使われる名前は、router.js

src
│ App.vue
│ main.js
router.js

├─assets
│  logo.png

└─components
   HelloWorld.vue

router.jsの中にRouterプラグインを使用できるように設定していく。

import Vue from 'vue';
import Router from 'vue-router';

Vue.use(Router);

export default new Router({
    routes: [{},{}]
});

関連付けをさせたいコンポーネントをインポートして、
routes: [{},{}]のオブジェクトの中に、パスとコンポネントを関連付ける。

import Vue from 'vue';
import Router from 'vue-router';
import Home from './views/Home.vue';
import Users from './views/Users.vue';


Vue.use(Router);

export default new Router({
    routes: [{ path: '/home', component: Home },
    { path: '/users', component: Users }]
});

main.jsでrouterをインポートさせる。
router.jsでRouterプラグインを使えるようにしているため、main.js上でrouter.jsをインポートする事で、vueインスタンス上で「router」が使用できるようになる。

import Vue from 'vue'
import App from './App.vue'
import router from './router.js'

Vue.config.productionTip = false

new Vue({
  router,
  render: h => h(App),
}).$mount('#app')

App.vueで<router-view>タグを使用して動的コンポーネントを表示させる。

<template>
  <div>
    <router-view></router-view>
  </div>
</template>

RouterのURLに「#」が付く理由

従来のマルチページアプリケーションでは、それぞれのURLに対応するhtmlを用意して、アクセスをしていた。
VueRouterでは、どんなページにアクセスしてもindex.htmlを表示させる処理を行っている。この仕組みが シングルページアプリケーション(SPA)である。
「#」以降のURLを頼りに動的コンポーネントを表示させているだけであって、URLが変わってもネットワークは動かない。
ブラウザーにとって、#はidを指定する場所という認識であるため、#以降のURLが変わってもインターネットは動かない。

「#」を外す方法

router.jsの設定でmodeを追記するだけで「#」を外すことができる。
デフォルトではhashになっている。

mode:”history”

export default new Router({
    mode:"history",
    routes: [{ path: '/home', component: Home },
    { path: '/users', component: Users }]
});

#を外すとURLが変わるごとにアクセスがされるが、node.jsが裏側で必ずindex.htmlを返している

公開する時は、全てのパスにindexを返す設定を行う必要がある。
公式サイト サーバー設定方法

aタグを使わないURLの切り替え方法

aタグを使用したリンクは、切り替える度にネットワークアクセスをしてしまう。アクセスする度、全てのJSを取得するため表示が遅くなる。
SPAのように通信をせずに動的コンポーネントを切り替える場合は、<router-link>タグを使用する。

<nav>
  <router-link to="/home">Home</router-link>
  <router-link to="/users">Users</router-link>
</nav>

router-linkは、ソース表示するタグを指定することもできる。
※デフォルトaタグ表示

<router-link to="/home" tag="div">Home</router-link>

to属性をv-bindを使って動的にする

URLを指定するto属性を動的にするには、v-bind(省略型[:])を用いる。

<router-link :to="'/home/' + (Number(id) + 1)">次のページ</router-link>

数値として演算を行う場合、要素がすべてString型になってしまうので、Number型にキャストする必要がある。

toの値をオブジェクトにする

nameをつかって、パスルートに任意の名称を付ける。

name:”users-age”

export default new Router({
    routes: [{ path: '/users/:id', 
            component: Users, props: true, 
            children: [{ path: 'name', 
                       component: UsersName }, 
                      { path: 'age', 
                       component: UsersAge,
                       name:"users-age"}] }]
});

toでnameを使ってパスルートを指定する。

<router-link :to="{name:'users-age'>次のページ</router-link>

~/id/のパラメータ情報をパスに含みたい時、paramsをオブジェクトに追加することができる。

<router-link :to="{name:'users-age',params:{id:Number(id)+1}}">次のページ</router-link>

queryもパラメータと同じようにオブジェクトに入れる事ができる。
queryとは、URLで?や=で表現されるもの。

<router-link :to="{name:'users-age',params:{id:Number(id)+1},query:{lang:'ja'}}">次のページ</router-link>

activeなリンクを取得する

active-class属性を付与することで、現在アクティブなリンクをつかむことができる。 toで指定したパスを表示している時に有効になる。

<nav>
  <router-link to="/home" tag="div" active-class="active">Home</router-link>
  <router-link to="/users" active-class="active">Users</router-link>
</nav>

<style scoped>
.active{
  color: red;
} 
</style>

/homeを例にとると、/home/123456など、homeの子階層を表示している場合もhomeがアクティブになる。/homeのみアクティブにし、子階層を表示している時は非アクティブにしたい場合、exact属性を付与する。
exact属性は、toで指定しているURLとイコールの時しかアクティブにならない命令を与える事ができる。

<router-link to="/home" tag="div" active-class="active" exact>Home</router-link>

JavaScriptからURLを切り替える

イベントでURLを切り替えることもできる。
$routerはナビゲーションで用いられる。URLを切り替えたり等。情報を取得する時に用いる$routeと混在しないように注意する。

<template>
  <div>
    <h1>Home</h1>
    <button @click="toUsers">Usersページへ移動する</button>
  </div>
</template>

<script>
export default {
  methods: {
    toUsers() {
      this.$router.push({ path: "users" });
    }
  }
};
</script>

動的URLを作る

/users/idのようなURLを作るには、router.jsに動的となるキーを設定する。
コロンで繋げて書く。

/users/:id

routes:[{ path: '/users/:id', component: Users }]

<メモ>
アクセスしたidの値(パラメータ)を確認するコード

<template>
  <div>
    <h1>Users</h1>
    <p>id:{{$route.params.id}}</p>
  </div>
</template>

動的URLは、ライフサイクルフックが生成されない。
watchを使って、変化を取得する。

export default {
    watch:{
        $route(to,from){
            // eslint-disable-next-line no-console
            console.log(to);
            // eslint-disable-next-line no-console
            console.log(from);

        }
    }
};

動的URLのルートはpropsを使って下記のように汎用性を持たせることが可能。
,props:true

routes: [{ path: '/users/:id', component: Users,props:true }]
export default {
    props:["id"]
};

パラメータを表示する場所では、propsの値を{{}}に代入するだけ。

<p>id:{{id}}</p>

子コンポーネントの中に router-view を作る

子コンポーネントの中にRouterを設ける時は、childrenを使用する。

Routerを使いたいコンポーネントのroutesにchildrenを作り、その中でまたパスとコンポーネントの紐づけを指定する。

export default new Router({
    routes: [{ path: '/users/:id', 
            component: Users, 
            props: true, 
            children: [{ path: 'name', component: UsersName },  
                     { path: 'age', component: UsersAge }] }]
});

タイトルとURLをコピーしました