Vue.js

#2 Vue.js基礎(v-vind)

kurumin

マスタッシュ構文はタグとタグに囲まれた部分(要素のテキスト)にしか使えない。
属性にテンプレート変数を利用したい場合は、データバインディングのディレクティブを利用する。

ディレクティブとは

テンプレートブロックでHTMLタグ内に記述するv-で始まる属性のこと。

ディレクティブ役割
v-vindデータバインディング
v-onイベント処理
v-model双方向データバインディング
v-htmlHTML文字列表示
v-pre静的コンテンツ表示
v-onceデータバインディングを初回のみに制限
v-clockマスタッシュ構文の非表示
v-if条件分岐
v-show表示/非表示の制御
v-forループ処理

本記事ではv-onの学習をする。(v-vindは次回)

属性にデータバインドするv-vind

<script setup lang="ts">
import { ref } from "vue";

const url = ref("https://vue.js.org/")
</script>

<template>
  <!-- 基本的な記述 -->
  <p><a v-bind:href="url" target="_blank">Vue.jsのサイト</a></p>
  <!-- 省略した記述。可読性という視点では非推奨。 -->
  <p><a :href="url" target="_blank">Vue.jsのサイト(省略形)</a></p>
  <!-- 式が記述できる -->
  <p><a v-bind:href="url + 'guide/introduction.html'" target="_blank">Vue.jsガイドのぺージ</a></p>
</template>
v-bind:△△=”〇〇”

要素の△△の属性として、テンプレート変数〇〇の値を設定する

属性(△△)の部分をディレクティブの引数という。

属性値のない属性へのバインド

disabledやreadonlyなど、属性値のない属性にもv-bindを使うことができる。

値としてtruefalseを使用する。

<script setup lang="ts">
import { ref } from "vue";

const isSendButtonDisabled = ref(true);
</script>

<template>
  <p><button type="button" v-bind:disabled="isSendButtonDisabled">送信</button></p>
</template>

バインドする属性をテンプレート変数として指定

ブラケット[]を使用すると属性をテンプレート変数として指定できる。

v-bindの引数もテンプレート変数で指定する方法を動的引数という。

<script setup lang="ts">
import { ref } from "vue";

const widthOrHeight = ref("height");
const widthOrHeightValue = ref(100);
</script>

<template>
  <p><img src="./assets/logo.svg" alt="" v-bind:[widthOrHeight]="widthOrHeightValue"></p>
</template>

複数の属性にまとめてバインドする

引数を指定せずにv-bindを使うと、複数の属性をまとめてバインドできる。

<script setup lang="ts">
import { ref } from "vue";

const imgAttributes = ref({
  src: "/images/logo.svg",
  alt: "Vueのロゴ",
  width: 75,
  height: 75
});
</script>

<template>
  <p><img v-bind="imgAttributes"></p>
</template>

<!-- レンダリング結果 -->
<p><img src="/images/logo.svg" alt="Vueのロゴ" width="75" height="75"></p>

なお、imgタグに直接属性を記述した場合、v-bindよりも直接記述した値の方が優先される。

style属性へのバインディング

<script setup lang="ts">
import { ref, computed } from "vue";

const msg = ref("スタイル属性へバインディング");
const msgTextRed = ref("red");
const msgTextColor = ref("white");
const msgBgColor = ref("black");

const msgStyles = ref({
  color: "white",
  backgroundColor: "black"
});

const msgStyles2 = ref({
  fontSize: "24px"
});

const msgStyles3 = ref({
  color: "pink",
  fontSize: "24px"
});

// 文字サイズをランダムで変更
const textSize = computed(
  (): string => {
    const size = Math.round(Math.random() * 25) + 10;
    return `${size}pt`;

  }
);
</script>

<template>
  <p v-bind:style="{ color: msgTextRed }">①{{ msg }}</p>
  <p v-bind:style="{ color: 'pink' }">②{{ msg }}</p>
  <!-- 文字サイズをランダムで変更 -->
  <p v-bind:style="{ fontSize: textSize }">③{{ msg }}</p>
  <!-- 複数のCSSを指定。スタイルプロパティはキャメル記法で記述する必要があるが、''を付ければケバブ記法でも動作する -->
  <p v-bind:style="{ color: msgTextRed, backgroundColor: msgBgColor }">④{{ msg }}</p>
  <p v-bind:style="{ color: msgTextRed, 'background-color': msgBgColor }">⑤{{ msg }}</p>
  <!-- オブジェクト側でCSSを複数指定 -->
  <p v-bind:style="msgStyles">⑥{{ msg }}</p>
  <!-- オブジェクトを配列として指定 -->
  <p v-bind:style="[msgStyles, msgStyles2]">⑦{{ msg }}</p>
  <!-- 複数のオブジェクトで同一のプロパティが指定されていた場合は、後に記述したオブジェクトで上書きされる -->
  <p v-bind:style="[msgStyles, msgStyles3]">⑧{{ msg }}</p>
  <p v-bind:style="[msgStyles3, msgStyles]">⑨{{ msg }}</p>
</template>

レンダリング結果は以下。

<p style="color: red;">①スタイル属性へバインディング</p>
<p style="color: pink;">②スタイル属性へバインディング</p>
<p style="font-size: 35pt;">③スタイル属性へバインディング</p>
<p style="color: red; background-color: black;">④スタイル属性へバインディング</p>
<p style="color: red; background-color: black;">⑤スタイル属性へバインディング</p>
<p style="color: white; background-color: black;">⑥スタイル属性へバインディング</p>
<p style="color: white; background-color: black; font-size: 24px;">⑦スタイル属性へバインディング</p>
<p style="color: pink; background-color: black; font-size: 24px;">⑧スタイル属性へバインディング</p>
<p style="color: white; font-size: 24px; background-color: black;">⑨スタイル属性へバインディング</p>
v-bind:style
v-bind:style="{スタイルプロパティ: 値, ・・・}"

スタイルプロパティはキャメル記法(fontSize、backgroundColorなど)で記述する。

class属性へのバインディング

style属性へのバインディングも可能だが、メンテナンス性を考えるとクラス名を利用したclass属性へのバインディングの方が望ましい。
この場合は、v-bind:classを利用する。

<script setup lang="ts">
import { ref, computed } from "vue";

const msg = ref("クラス属性へバインディング");
// スタイル適用の有無はtrueかfalseで指定する。
const isTextColorRed = ref(true);
const isBgColorBlue = ref(false);

const styles = ref({
  textColorRed: false,
  bgColorBlue: true
});

const computedStyles = computed(
  (): { textColorRed: boolean; bgColorBlue: boolean; } => {
    // 乱数を利用して0か1を生成(TextColorRed用)
    const randText = Math.round(Math.random());
    // textColorRedプロパティの値を表す変数をtrueで用意。
    let textColorFlg = true;
    // 発生した乱数が0ならばfalseに変数。
    if (randText == 0) {
      textColorFlg = false;
    }

    // 乱数を利用して0か1を生成(bgColorBlue用)
    const randBg = Math.round(Math.random());
    // bgColorBlueプロパティの値を表す変数をtrueで用意。
    let bgColorFlg = true;
    // 発生した乱数が0ならばfalseに変数。
    if (randBg == 0) {
      bgColorFlg = false;
    }

    // それぞれのプロパティの値をオブジェクトにして返す。
    return {
      textColorRed: textColorFlg,
      bgColorBlue: bgColorFlg
    }
  });
</script>

<template>
  <p v-bind:class="{ textColorRed: true, bgColorBlue: true }">{{ msg }}</p>
  <p v-bind:class="{ textColorRed: isTextColorRed, bgColorBlue: isBgColorBlue }">{{ msg }}</p>
  <!-- textColorPinkではCSSは適用されない -->
  <p v-bind:class="{ textColorPink: true }">{{ msg }}</p>
  <!-- クラス名をプロパティに指定する場合は、''で囲む -->
  <p v-bind:class="{ 'text-color-pink': true }">{{ msg }}</p>
  <!-- v-bind:classはclass属性と併用できる -->
  <p class="textSize24" v-bind:class="{ textColorRed: isTextColorRed, bgColorBlue: isBgColorBlue }">{{ msg }}</p>
  <!-- オブジェクトの指定も可能 -->
  <p class="textSize24" v-bind:class="styles">{{ msg }}</p>
  <!-- 算出プロパティの指定も可能 -->
  <p v-bind:class="computedStyles">{{ msg }}</p>
</template>

<style scoped>
.textColorRed {
  color: red;
}

.text-color-pink {
  color: pink
}

.bgColorBlue {
  background-color: blue;
}

.textSize24 {
  font-size: 24px;
}
</style>
オブジェクトの型指定
 (): { textColorRed: boolean; bgColorBlue: boolean; }

:(コロン)の右側は、この関数の戻り値を表す。

{
  プロパティ名: データ型;
}

このようにすることで戻り値オブジェクトのプロパティとその型が保証できる。

レンダリング結果は以下。

<p data-v-7a7a37b1="" class="textColorRed bgColorBlue">クラス属性へバインディング</p>
<p data-v-7a7a37b1="" class="textColorRed">クラス属性へバインディング</p>
  <!-- textColorPinkではCSSは適用されない -->
<p data-v-7a7a37b1="" class="textColorPink">クラス属性へバインディング</p>
  <!-- クラス名をプロパティに指定する場合は、''で囲む -->
<p data-v-7a7a37b1="" class="text-color-pink">クラス属性へバインディング</p>
  <!-- v-bind:classはclass属性と併用できる -->
<p data-v-7a7a37b1="" class="textSize24 textColorRed">クラス属性へバインディング</p>
  <!-- オブジェクトの指定も可能 -->
<p data-v-7a7a37b1="" class="textSize24 bgColorBlue">クラス属性へバインディング</p>
  <!-- 算出プロパティの指定も可能 -->
<p data-v-7a7a37b1="" class="textColorRed bgColorBlue">クラス属性へバインディング</p>

ABOUT ME
記事URLをコピーしました