Web素人がVueのtutorialをやってみる その3 (Step7/15 ～ Step8/15 まで)

## 概要
[前回](https://qiita.com/tak_y07/items/13b6925e8a0e3a792014)に引き続きVueのtutorialをやっていきます。Step7からの続きです。
今回も変なところで終わるかも…

## 先におまけ
ポモドーロに[こちら](https://store.steampowered.com/app/2113850/Spirit_City_Lofi_Sessions/?l=japanese)のゲームみたいなものを使っています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3759711/44531542-3fa1-1eff-bc42-f2f282c4de57.png)

以下の機能を備えていてオススメです。
- 作業用BGM
- タスクTODO
- 習慣TODO
- メモ

この記事で一番有益な情報だな！（オイ）


## Step7
リストレンダリングについて

### v-forディレクティブ
v-forディレクティブで配列要素のレンダリングが可能

```Step6Sample.vue
<ul>
  <li v-for="todo in todos" :key="todo.id">
    {{ todo.text }}
  </li>
</ul>
```
上記での`todo`のスコープは通常の関数のようにディレクティブで指定されている内部の要素にまで有効。

## Step7実践
TODOリストのアイテムの追加と削除ができるように以下を修正する。

```Step7.vue
<script>
// give each todo a unique id
let id = 0

export default {
  data() {
    return {
      newTodo: '',
      todos: [
        { id: id++, text: 'Learn HTML' },
        { id: id++, text: 'Learn JavaScript' },
        { id: id++, text: 'Learn Vue' }
      ]
    }
  },
  methods: {
    addTodo() {
      // ...
      this.newTodo = ''
    },
    removeTodo(todo) {
      // ...
    }
  }
}
</script>

<template>
  <form @submit.prevent="addTodo">
    <input v-model="newTodo" required placeholder="new todo">
    <button>Add Todo</button>
  </form>
  <ul>
    <li v-for="todo in todos" :key="todo.id">
      {{ todo.text }}
      <button @click="removeTodo(todo)">X</button>
    </li>
  </ul>
</template>
```

修正後が下記
```Step7Ans.vue
<script>
// give each todo a unique id
let id = 0

export default {
  data() {
    return {
      newTodo: '',
      todos: [
        { id: id++, text: 'Learn HTML' },
        { id: id++, text: 'Learn JavaScript' },
        { id: id++, text: 'Learn Vue' }
      ]
    }
  },
  methods: {
    addTodo() {
      this.todos.push({ id: id++, text: this.newTodo })
      this.newTodo = ''
    },
    removeTodo(todo) {
      this.todos = this.todos.filter(
        function(temp){
        	if (temp !== todo){
          	return temp
        	}
      	}
     	)
    }
  }
}
</script>

<template>
  <form @submit.prevent="addTodo">
    <input v-model="newTodo" required placeholder="new todo">
    <button>Add Todo</button>
  </form>
  <ul>
    <li v-for="todo in todos" :key="todo.id">
      {{ todo.text }}
      <button @click="removeTodo(todo)">X</button>
    </li>
  </ul>
</template>
```

結果
どっちかと言わなくても`filter`の使い方の方に苦戦…
JSの知識不足が如実に効き始めている…
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3759711/e5e4c13b-3eb7-4b7f-9046-c09f2f1b506d.png)

# Step8
算術プロパティ：Computedオプションについて

Computed内でリアクティブなプロパティを参照している関数は、そのプロパティの変更に伴い自動で実行される。また、その計算結果はキャッシュされる。

下記の例では、
- リアクティブなプロパティ(のうちComputedで参照されているもの) = hideCompleted
- リアクティブなプロパティを参照しているComputed内の関数 = filteredTodos
であり、hideCompletedの値が変わるたびに、filterdTodosが実行されている。
```Step8Ans.vue
<script>
let id = 0

export default {
  data() {
    return {
      newTodo: '',
      hideCompleted: false,
      todos: [
        { id: id++, text: 'Learn HTML', done: true },
        { id: id++, text: 'Learn JavaScript', done: true },
        { id: id++, text: 'Learn Vue', done: false }
      ]
    }
  },
  computed: {
    filteredTodos(){
      return this.hideCompleted
        ? this.todos.filter((t)=>!t.done)
      	: this.todos
    }
    // ...
  },
  methods: {
    addTodo() {
      this.todos.push({ id: id++, text: this.newTodo, done: false })
      this.newTodo = ''
    },
    removeTodo(todo) {
      this.todos = this.todos.filter((t) => t !== todo)
    }
  }
}
</script>

<template>
  <form @submit.prevent="addTodo">
    <input v-model="newTodo" required placeholder="new todo">
    <button>Add Todo</button>
  </form>
  <ul>
    <li v-for="todo in filteredTodos" :key="todo.id">
      <input type="checkbox" v-model="todo.done">
      <span :class="{ done: todo.done }">{{ todo.text }}</span>
      <button @click="removeTodo(todo)">X</button>
    </li>
  </ul>
  <button @click="hideCompleted = !hideCompleted">
    {{ hideCompleted ? 'Show all' : 'Hide completed' }}
  </button>
</template>

<style>
.done {
  text-decoration: line-through;
}
</style>
```

結果
「HideCompleted」をクリックすると「掃除」が隠れる
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3759711/0561a68e-4150-2fd2-3a08-6c51d724da96.png)

## 続く
今回はここまで。
明日ホムセン行かなきゃ…