Search.vue 2.6 KB
Newer Older
1
2
<template>
  <div>
3
    <h2><translate>Search for some music</translate></h2>
4
5
6
7
8
9
10
    <div :class="['ui', {'loading': isLoading }, 'search']">
      <div class="ui icon big input">
        <i class="search icon"></i>
        <input ref="search" class="prompt" placeholder="Artist, album, track..." v-model.trim="query" type="text" />
      </div>
    </div>
    <template v-if="query.length > 0">
11
      <h3 class="ui title"><translate>Artists</translate></h3>
12
13
14
15
16
      <div v-if="results.artists.length > 0" class="ui stackable three column grid">
        <div class="column" :key="artist.id" v-for="artist in results.artists">
          <artist-card class="fluid" :artist="artist" ></artist-card>
        </div>
      </div>
17
      <p v-else><translate>Sorry, we did not found any artist matching your query</translate></p>
18
19
    </template>
    <template v-if="query.length > 0">
20
      <h3 class="ui title"><translate>Albums</translate></h3>
21
22
23
24
25
      <div v-if="results.albums.length > 0" class="ui stackable three column grid">
        <div class="column" :key="album.id" v-for="album in results.albums">
          <album-card class="fluid" :album="album" ></album-card>
        </div>
      </div>
26
      <p v-else><translate>Sorry, we did not found any album matching your query</translate></p>
27
28
29
30
31
    </template>
  </div>
</template>

<script>
32
import _ from 'lodash'
Eliot Berriot's avatar
Eliot Berriot committed
33
import axios from 'axios'
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
import logger from '@/logging'
import AlbumCard from '@/components/audio/album/Card'
import ArtistCard from '@/components/audio/artist/Card'

export default {
  components: {
    AlbumCard,
    ArtistCard
  },
  props: {
    autofocus: {type: Boolean, default: false}
  },
  data () {
    return {
      query: '',
      results: {
        albums: [],
        artists: []
      },
53
      isLoading: false
54
55
56
57
58
59
60
61
62
    }
  },
  mounted () {
    if (this.autofocus) {
      this.$refs.search.focus()
    }
    this.search()
  },
  methods: {
63
    search: _.debounce(function () {
64
65
66
67
68
69
70
71
72
      if (this.query.length < 1) {
        return
      }
      var self = this
      self.isLoading = true
      logger.default.debug('Searching track matching "' + this.query + '"')
      let params = {
        query: this.query
      }
Eliot Berriot's avatar
Eliot Berriot committed
73
74
      axios.get('search', {
        params: params
75
76
77
78
      }).then((response) => {
        self.results = self.castResults(response.data)
        self.isLoading = false
      })
79
    }, 500),
80
81
    castResults (results) {
      return {
82
83
        albums: results.albums,
        artists: results.artists
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
      }
    }
  },
  watch: {
    query () {
      this.search()
    }
  }
}
</script>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>

</style>