💦

vue の template 上で 変数を宣言したい。そういう時のアプローチ

2025/04/09に公開

まず

Vue3 では ジェネリクス が使えます。

https://ja.vuejs.org/api/sfc-script-setup.html#generics

vuejs では スコープ付きスロット を使うことで template 上で 変数を宣言することができます。

また、 default スロットであれば template 要素も省略できます。

https://ja.vuejs.org/guide/components/slots#scoped-slots

アプローチ

具体的なアプローチとしては

まず、 型引数 T を使うこととします。

任意の型を Props に直接渡すことはできない為、一旦 value プロパティを T 型として公開します。

また、スコープ付き スロットとして default スロット の引数を T 型とします。

つまり、こういう実装になります。

PassThrough.vue
<script setup lang="ts" generic="T">
export interface PassThroughProps<T> {
  value: T;
}
export interface PassThroughSlots<T> {
  default(props: T): any
}
defineOptions({
  inheritAttrs: false,
});
const props = defineProps<PassThroughProps<T>>()
defineSlots<PassThroughSlots<T>>();
</script>
<template>
  <slot name="default" v-bind="props.value"></slot>
</template>

使う時はこんな感じです。

App.vue
<script setup lang="ts">
import PassThrough from "./PassThrough.vue";
</script>
<template>
  <PassThrough :value="{ hello: 'hello', world: 'world' }" v-slot="{ hello, world }">
    <div class="hello">{{ `${hello} ${world}` }}</div>
  </PassThrough>
</template>

これにより PassThroughvalue プロパティに渡した値が v-slot:default の変数として取得できます。

playground

以上。

Discussion