Vue.jsでObjectを子コンポーネントにpropsで渡すいくつかの方法
いくつかの方法
だいたい4つぐらいがありそう。
- いくつかの方法
- 環境
- Objectをそのまま渡す
- Object内でプロパティを指定し渡す
- プロパティのみを渡す
- Objectを省略記法を使いそのまま渡す
- どれがいいのか
- どれを使うべきか
- 備考導入編
- srcフォルダ
- 成果物
- 参考文献
環境
- 【Editor】: VS Code
- 【Terminal】: Iterm2
- 【Shell】: zsh
- 【PackageManager】: Yarn
- 【Vue Style】: Vue Class Style Component
- 【Vue Script Language Block】: TypeScript
Objectをそのまま渡す
親コンポーネント
<template> <div id="app"> <ChildComponent :porps-for-child="propsForChild"/> </div> </template> <script lang="ts"> import { Component, Vue } from 'vue-property-decorator'; import ChildComponent from './components/ChildComponent.vue'; @Component({ components: { ChildComponent, }, }) export default class App extends Vue { propsForChild = { from: 'Parent', to: 'Child', } } </script>
子コンポーネント
<template> <p>{{ propsForChild }}</p> </template> <script lang="ts"> import { Component, Prop, Vue } from 'vue-property-decorator'; type PropsForChild = { from: string, to: string } @Component export default class ChildComponent extends Vue { @Prop() private propsForChild!: PropsForChild; } </script>
Object内でプロパティを指定し渡す
親コンポーネント
<template> <div id="app"> <ChildComponent :porps-for-child="{ from: 'Parent', to: 'Child' }"/> </div> </template> <script lang="ts"> import { Component, Vue } from 'vue-property-decorator'; import ChildComponent from './components/ChildComponent.vue'; @Component({ components: { ChildComponent, }, }) export default class App extends Vue { propsForChild = { from: '', to: '', } } </script>
子コンポーネント
<template> <p>{{ propsForChild }}</p> </template> <script lang="ts"> import { Component, Prop, Vue } from 'vue-property-decorator'; type PropsForChild = { from: string, to: string } @Component export default class ChildComponent extends Vue { @Prop() private propsForChild!: PropsForChild; } </script>
プロパティのみを渡す
親コンポーネント
<template> <div id="app"> <ChildComponent :from="propsForChild.from" :to="propsForChild.to" /> </div> </template> <script lang="ts"> import { Component, Vue } from 'vue-property-decorator'; import ChildComponent from './components/ChildComponent.vue'; @Component({ components: { ChildComponent, }, }) export default class App extends Vue { propsForChild = { from: 'Parent', to: 'Child', } } </script>
子コンポーネント
<template> <p>{{ from }} {{ to }}</p> </template> <script lang="ts"> import { Component, Prop, Vue } from 'vue-property-decorator'; @Component export default class ChildComponent extends Vue { @Prop() private from!: string; @Prop() private to!: string; } </script>
Objectを省略記法を使いそのまま渡す
親コンポーネント
<template> <div id="app"> <ChildComponent v-bind="propsForChild"/> </div> </template> <script lang="ts"> import { Component, Vue } from 'vue-property-decorator'; import ChildComponent from './components/ChildComponent.vue'; @Component({ components: { ChildComponent, }, }) export default class App extends Vue { propsForChild = { from: 'Parent', to: 'Child', } } </script>
子コンポーネント
<template> <p>{{ from }} {{ to }}</p> </template> <script lang="ts"> import { Component, Prop, Vue } from 'vue-property-decorator'; @Component export default class ChildComponent extends Vue { @Prop() private from!: string; @Prop() private to!: string; } </script>
どれがいいのか
Objectをそのまま渡す
- メリット
- 親のtemplate内の見通しがよくなる
- 値のバケツリレーする量が多くなると見やすい
- デメリット
- どんなプロパティを渡しているかtemplate内からでは判断できない
- 中継をするようなコンポーネントならなおさらどんなプロパティを渡しているか分からない
- TypeScriptでtypeを付けないと辛い
Object内でプロパティを指定し渡す
- メリット
- どんなpropsでどんなプロパティを渡すのか明確
- デメリット
- そのままObjectを渡すよりも冗長な感じ
- TypeScriptでtypeを付けないと辛い
プロパティのみを渡す
- メリット
- 子コンポーネントで具体的にpropsの指定を書くことができる
- どんな値を受け渡すのか分かりやすい
- 子コンポーネント側で標準のvueを使い具体的な型について書ける
- デメリット
- 値のバケツリレーする量が多くなると見づらい
- templateの風通しが悪い
Objectを省略記法を使いそのまま渡す
- メリット
- Objectをそのまま渡すよりも短く書くことができるかもしれない
- 子コンポーネントで具体的にpropsの指定を書くことができる
- 子コンポーネント側で標準のvueを使い具体的な型について書ける
- デメリット
- どんな値を受け渡すのか分かりにくい
- 省略記法への知識がいる
どれを使うべきか
一概にこれのみを使えとは言えない。どれがいいのか設計に応じて決めるべきな感じ。
個人的には、Object内でプロパティを指定し渡す方法を使うようにした方がいい気がする。この書き方で、TypeScriptで型を付けて、vueのrequired等のオプションを付けて、computedでObjectを綺麗に分けるのがbetterな感じがする。
備考導入編
今回のobjectをpropsに渡すにあたり作成した流れを記す。
vue cliがどうなってた確認。
~/development 28s ❯ yarn global list yarn global v1.9.2 info "@vue/cli@3.0.0-rc.4" has binaries: - vue
うん。古いね。
アップデート。
~/development ❯ yarn global add @vue/cli yarn global v1.15.2 〜〜〜中略〜〜〜 success Installed "@vue/cli@3.7.0" with binaries: - vue ✨ Done in 27.11s.
一応しっかし、バージョンアップできてるか確認。
~/development 7s ❯ vue --version 3.7.0
じゃあプロジェクト作成するぞ!
~/development ❯ vue create vue-props-test Vue CLI v3.7.0 ? Please pick a preset: Manually select features ? Check the features needed for your project: Babel, TS, Linter ? Use class-style component syntax? Yes ? Use Babel alongside TypeScript for auto-detected polyfills? Yes ? Pick a linter / formatter config: Airbnb ? Pick additional lint features: Lint on save ? Where do you prefer placing config for Babel, PostCSS, ESLint, etc.? In dedicated config files ? Save this as a preset for future projects? No 〜〜〜中略〜〜〜 success Saved lockfile. ✨ Done in 22.84s. ⚓ Running completion hooks... 📄 Generating README.md... 🎉 Successfully created project vue-props-test. 👉 Get started with the following commands: $ cd vue-props-test $ yarn serve
できたので、コマンドを実行して、vscodeを開く。
cd vue-props-test
code .
srcフォルダ
どんな感じにsrcフォルダができているか見る。
~/development/vue-props-test master ❯ tree ./src ./src ├── App.vue ├── assets │ └── logo.png ├── components │ └── HelloWorld.vue ├── main.ts ├── shims-tsx.d.ts └── shims-vue.d.ts 2 directories, 6 files
↑を↓にする。
~/development/vue-props-test master* ❯ tree ./src ./src ├── App.vue ├── components │ └── ChildComponent.vue ├── main.ts ├── shims-tsx.d.ts └── shims-vue.d.ts
成果物
https://github.com/tomatoaiu/vue-props-sample
参考文献
- Vue.js,入手先 https://jp.vuejs.org/
- 作者:MIO
- 発売日: 2018/05/29
- メディア: Kindle版