1/*
2 * Copyright (C) 2016, 2017
3 *      Jean-Luc Barriere <jlbarriere68@gmail.com>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; version 3.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
16 */
17
18import QtQuick 2.9
19import QtQuick.Controls 2.2
20import QtQuick.Layouts 1.3
21import NosonApp 1.0
22import "components"
23import "components/Delegates"
24import "components/Flickables"
25import "components/Dialog"
26
27MusicPage {
28    id: playlistsPage
29    objectName: "playlistsPage"
30    pageTitle: qsTr("Playlists")
31    pageFlickable: playlistsGrid
32    searchable: true
33    addVisible: true
34
35    property bool changed: false
36    property bool childrenChanged: false
37
38    onSearchClicked: filter.visible = true
39
40    header: MusicFilter {
41        id: filter
42        visible: false
43    }
44
45    SortFilterModel {
46        id: playlistsModelFilter
47        model: AllPlaylistsModel
48        sort.property: "title"
49        sort.order: Qt.AscendingOrder
50        sortCaseSensitivity: Qt.CaseInsensitive
51        filter.property: "normalized"
52        filter.pattern: new RegExp(normalizedInput(filter.displayText), "i")
53        filterCaseSensitivity: Qt.CaseInsensitive
54    }
55
56    MusicGridView {
57        id: playlistsGrid
58        itemWidth: units.gu(15)
59        heightOffset: units.gu(7)
60
61        model: playlistsModelFilter
62
63        delegate: Card {
64            id: playlistCard
65            height: playlistsGrid.cellHeight
66            width: playlistsGrid.cellWidth
67            primaryText: model.title
68            secondaryTextVisible: false
69
70            isFavorite: (AllFavoritesModel.findFavorite(model.payload).length > 0)
71
72            // check favorite on data loaded
73            Connections {
74                target: AllFavoritesModel
75                function onLoaded(succeeded) {
76                    isFavorite = (AllFavoritesModel.findFavorite(model.payload).length > 0)
77                }
78            }
79
80            coverSources: allCovers()
81
82            function allCovers() {
83                var cs = [];
84                var arts = model.arts;
85                for (var i = 0; i < arts.length; ++i) cs.push({art: arts[i]});
86                return cs;
87            }
88
89            coverFlow: 4
90
91            onClicked: {
92                stackView.push("qrc:/controls2/SongsView.qml",
93                                   {
94                                       "containerItem": makeContainerItem(model),
95                                       "songSearch": model.id,
96                                       "album": undefined,
97                                       "coverFlow": 4,
98                                       "covers": coverSources,
99                                       "isPlaylist": true,
100                                       "genre": undefined,
101                                       "page": playlistsPage,
102                                       "pageTitle": qsTr("Playlist"),
103                                       "line1": "",
104                                       "line2": model.title,
105                                   })
106            }
107            onPressAndHold: {
108                if (isFavorite && removeFromFavorites(model.payload))
109                    isFavorite = false
110                else if (!isFavorite && addItemToFavorites(model, qsTr("Playlist"), imageSource))
111                    isFavorite = true
112            }
113        }
114    }
115
116    // Overlay to show when no playlists are on the device
117    Loader {
118        anchors.fill: parent
119        active: AllPlaylistsModel.count === 0 && !infoLoadedIndex
120        asynchronous: true
121        source: "qrc:/controls2/components/PlaylistsEmptyState.qml"
122        visible: active
123    }
124
125    DialogNewPlaylist {
126        id: dialogNewPlaylist
127    }
128
129    onAddClicked: dialogNewPlaylist.open()
130
131    // Overlay to show when load failed
132    Loader {
133        anchors.fill: parent
134        active: AllPlaylistsModel.failure
135        asynchronous: true
136        sourceComponent: Component {
137            DataFailureState {
138                onReloadClicked: AllPlaylistsModel.asyncLoad();
139            }
140        }
141        visible: active
142    }
143}
144