[vlc-commits] [Git][videolan/vlc][master] 15 commits: medialibrary: Add video(s) list and count functions
Hugo Beauzée-Luyssen (@chouquette)
gitlab at videolan.org
Sun Feb 20 15:40:10 UTC 2022
Hugo Beauzée-Luyssen pushed to branch master at VideoLAN / VLC
Commits:
a4e5e0ce by Pierre Lamot at 2022-02-20T14:18:57+00:00
medialibrary: Add video(s) list and count functions
Co-authored-by: Benjamin Arnaud <benjamin.arnaud at videolabs.io>
- - - - -
7866b1be by Pierre Lamot at 2022-02-20T14:18:57+00:00
medialibrary: Add audio(s) list and count functions
Co-authored-by: Benjamin Arnaud <benjamin.arnaud at videolabs.io>
- - - - -
6f2b25fa by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
medialibrary: Udpate folder support
- - - - -
5fa9fb97 by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt/covergenerator: Add folder support
- - - - -
21c57e14 by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt/mlhelper: Create the 'getVideoListCover' function
- - - - -
1066a20b by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt/mlvideomodel: Switch to list video(s) functions
- - - - -
4f02618c by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt/mlgrouplistmodel: Inherit from MLVideoModel
- - - - -
c536126d by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt: Rename MLGroupListModel to MLVideoGroupsModel
- - - - -
fd3245c2 by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt: Create MLFolder
- - - - -
877355ec by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt: Create MLVideoFoldersModel
- - - - -
724981ad by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt: Rename GroupListContextMenu to VideoGroupsContextMenu
- - - - -
1af0a999 by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt/qml_menu_wrapper: Add 'Group by folder' to SortMenuVideo
- - - - -
02dca7ec by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qt/qml_menu_wrapper: Create VideoFoldersContextMenu
- - - - -
712c7715 by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qml/VideoAllSubDisplay: Add folder support
- - - - -
6fb0c5f3 by Benjamin Arnaud at 2022-02-20T14:18:57+00:00
qml/MediaGroupDisplay: Fix the 'initialTitle' property
- - - - -
23 changed files:
- include/vlc_media_library.h
- modules/gui/qt/Makefile.am
- modules/gui/qt/maininterface/mainui.cpp
- modules/gui/qt/medialibrary/mlbasemodel.hpp
- + modules/gui/qt/medialibrary/mlfolder.cpp
- + modules/gui/qt/medialibrary/mlfolder.hpp
- modules/gui/qt/medialibrary/mlhelper.cpp
- modules/gui/qt/medialibrary/mlhelper.hpp
- modules/gui/qt/medialibrary/mlqmltypes.hpp
- + modules/gui/qt/medialibrary/mlvideofoldersmodel.cpp
- + modules/gui/qt/medialibrary/mlvideofoldersmodel.hpp
- modules/gui/qt/medialibrary/mlgrouplistmodel.cpp → modules/gui/qt/medialibrary/mlvideogroupsmodel.cpp
- modules/gui/qt/medialibrary/mlgrouplistmodel.hpp → modules/gui/qt/medialibrary/mlvideogroupsmodel.hpp
- modules/gui/qt/medialibrary/mlvideomodel.cpp
- modules/gui/qt/medialibrary/qml/MediaGroupDisplay.qml
- modules/gui/qt/medialibrary/qml/VideoAllSubDisplay.qml
- modules/gui/qt/menus/qml_menu_wrapper.cpp
- modules/gui/qt/menus/qml_menu_wrapper.hpp
- modules/gui/qt/util/covergenerator.cpp
- modules/misc/medialibrary/entities.cpp
- modules/misc/medialibrary/medialibrary.cpp
- modules/misc/medialibrary/medialibrary.h
- po/POTFILES.in
Changes:
=====================================
include/vlc_media_library.h
=====================================
@@ -334,9 +334,11 @@ typedef struct vlc_ml_playlist_list_t
typedef struct vlc_ml_folder_t
{
- int64_t i_id; /**< This folder's MRL. Will be NULL if b_present is false */
- char* psz_mrl; /**< This folder's MRL. Will be NULL if b_present is false */
- bool b_present; /**< The presence state for this folder. */
+ int64_t i_id; /**< The folder's MRL. Will be NULL if b_present is false */
+ char* psz_name; /**< The folder's name */
+ char* psz_mrl; /**< The folder's MRL. Will be NULL if b_present is false */
+ unsigned int i_nb_media; /**< The media count */
+ bool b_present; /**< The folder's presence state */
bool b_banned; /**< Will be true if the user required this folder to be excluded */
} vlc_ml_folder_t;
@@ -443,6 +445,8 @@ enum vlc_ml_list_queries
VLC_ML_COUNT_ENTRY_POINTS, /**< arg1 bool: list_banned; arg2 (out): size_t* */
VLC_ML_LIST_FOLDERS, /**< arg1 (out): vlc_ml_folder_list_t** */
VLC_ML_COUNT_FOLDERS, /**< arg1 (out): size_t* */
+ VLC_ML_LIST_FOLDERS_BY_TYPE, /**< arg1 vlc_ml_media_type_t: the media type. arg2 (out): vlc_ml_media_list_t** */
+ VLC_ML_COUNT_FOLDERS_BY_TYPE, /**< arg1 vlc_ml_media_type_t: the media type. arg2 (out): vlc_ml_media_list_t** */
/* Album specific listings */
VLC_ML_LIST_ALBUM_TRACKS, /**< arg1: The album id. arg2 (out): vlc_ml_media_list_t** */
@@ -484,12 +488,16 @@ enum vlc_ml_list_queries
/* Folder specific listings */
VLC_ML_LIST_SUBFOLDERS, /**< arg1: parent id; arg2 (out): vlc_ml_folder_list_t** */
VLC_ML_COUNT_SUBFOLDERS, /**< arg1: parent id; arg2 (out): size_t* */
- VLC_ML_LIST_FOLDER_MEDIAS, /**< arg1: folder id; arg2 (out): vlc_ml_media_list_t** */
- VLC_ML_COUNT_FOLDER_MEDIAS, /**< arg1: folder id; arg2 (out): size_t* */
+ VLC_ML_LIST_FOLDER_MEDIA, /**< arg1: folder id; arg2 (out): vlc_ml_media_list_t** */
+ VLC_ML_COUNT_FOLDER_MEDIA, /**< arg1: folder id; arg2 (out): size_t* */
/* Children entities listing */
VLC_ML_LIST_MEDIA_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): ml_media_list_t** */
VLC_ML_COUNT_MEDIA_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): size_t* */
+ VLC_ML_LIST_VIDEO_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): size_t* */
+ VLC_ML_COUNT_VIDEO_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): size_t* */
+ VLC_ML_LIST_AUDIO_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): size_t* */
+ VLC_ML_COUNT_AUDIO_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): size_t* */
VLC_ML_LIST_ARTISTS_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): ml_artist_list_t** */
VLC_ML_COUNT_ARTISTS_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): size_t* */
VLC_ML_LIST_ALBUMS_OF, /**< arg1: parent entity type; arg2: parent entity id; arg3(out): ml_album_list_t** */
@@ -504,6 +512,7 @@ enum vlc_ml_parent_type
VLC_ML_PARENT_SHOW,
VLC_ML_PARENT_GENRE,
VLC_ML_PARENT_GROUP,
+ VLC_ML_PARENT_FOLDER,
VLC_ML_PARENT_PLAYLIST,
};
@@ -1209,6 +1218,66 @@ static inline size_t vlc_ml_count_media_of( vlc_medialibrary_t* p_ml, const vlc_
return res;
}
+static inline vlc_ml_media_list_t* vlc_ml_list_video_of( vlc_medialibrary_t* p_ml,
+ const vlc_ml_query_params_t* params,
+ int i_parent_type, int64_t i_parent_id )
+{
+ vlc_assert( p_ml != NULL );
+
+ vlc_ml_media_list_t* res;
+
+ if ( vlc_ml_list( p_ml, VLC_ML_LIST_VIDEO_OF,
+ params, i_parent_type, i_parent_id, &res ) != VLC_SUCCESS )
+ return NULL;
+
+ return res;
+}
+
+static inline size_t vlc_ml_count_video_of( vlc_medialibrary_t* p_ml,
+ const vlc_ml_query_params_t* params,
+ int i_parent_type, int64_t i_parent_id )
+{
+ vlc_assert( p_ml != NULL );
+
+ size_t res;
+
+ if ( vlc_ml_list( p_ml, VLC_ML_COUNT_VIDEO_OF,
+ params, i_parent_type, i_parent_id, &res ) != VLC_SUCCESS )
+ return 0;
+
+ return res;
+}
+
+static inline vlc_ml_media_list_t* vlc_ml_list_audio_of( vlc_medialibrary_t* p_ml,
+ const vlc_ml_query_params_t* params,
+ int i_parent_type, int64_t i_parent_id )
+{
+ vlc_assert( p_ml != NULL );
+
+ vlc_ml_media_list_t* res;
+
+ if ( vlc_ml_list( p_ml, VLC_ML_LIST_AUDIO_OF,
+ params, i_parent_type, i_parent_id, &res ) != VLC_SUCCESS )
+ return NULL;
+
+ return res;
+}
+
+static inline size_t vlc_ml_count_audio_of( vlc_medialibrary_t* p_ml,
+ const vlc_ml_query_params_t* params,
+ int i_parent_type, int64_t i_parent_id )
+{
+ vlc_assert( p_ml != NULL );
+
+ size_t res;
+
+ if ( vlc_ml_list( p_ml, VLC_ML_COUNT_AUDIO_OF,
+ params, i_parent_type, i_parent_id, &res ) != VLC_SUCCESS )
+ return 0;
+
+ return res;
+}
+
static inline vlc_ml_artist_list_t* vlc_ml_list_artist_of( vlc_medialibrary_t* p_ml, const vlc_ml_query_params_t* params, int i_parent_type, int64_t i_parent_id )
{
vlc_assert( p_ml != NULL );
@@ -1693,6 +1762,93 @@ static inline size_t vlc_ml_count_banned_entry_points( vlc_medialibrary_t* p_ml,
return res;
}
+// Folders
+
+static inline vlc_ml_folder_list_t * vlc_ml_list_folders(vlc_medialibrary_t * p_ml,
+ const vlc_ml_query_params_t * params)
+{
+ vlc_assert(p_ml != NULL);
+
+ vlc_ml_folder_list_t * res;
+
+ if (vlc_ml_list(p_ml, VLC_ML_LIST_FOLDERS, params, &res) != VLC_SUCCESS)
+ return NULL;
+
+ return res;
+}
+
+static inline size_t vlc_ml_count_folders(vlc_medialibrary_t * p_ml,
+ const vlc_ml_query_params_t * params)
+{
+ vlc_assert(p_ml != NULL);
+
+ size_t count;
+
+ if (vlc_ml_list(p_ml, VLC_ML_COUNT_FOLDERS, params, &count) != VLC_SUCCESS)
+ return 0;
+
+ return count;
+}
+
+static inline
+vlc_ml_folder_list_t * vlc_ml_list_folders_by_type(vlc_medialibrary_t * p_ml,
+ const vlc_ml_query_params_t * params,
+ vlc_ml_media_type_t type)
+{
+ vlc_assert(p_ml != NULL);
+
+ vlc_ml_folder_list_t * res;
+
+ if (vlc_ml_list(p_ml, VLC_ML_LIST_FOLDERS_BY_TYPE, params, (int) type, &res) != VLC_SUCCESS)
+ return NULL;
+
+ return res;
+}
+
+static inline size_t vlc_ml_count_folders_by_type(vlc_medialibrary_t * p_ml,
+ const vlc_ml_query_params_t * params,
+ vlc_ml_media_type_t type)
+{
+ vlc_assert(p_ml != NULL);
+
+ size_t count;
+
+ if (vlc_ml_list(p_ml, VLC_ML_COUNT_FOLDERS_BY_TYPE, params, (int) type, &count) != VLC_SUCCESS)
+ return 0;
+
+ return count;
+}
+
+// Folder Media
+
+static inline vlc_ml_media_list_t * vlc_ml_list_folder_media(vlc_medialibrary_t * p_ml,
+ const vlc_ml_query_params_t * params,
+ int64_t i_folder_id)
+{
+ vlc_assert(p_ml != NULL);
+
+ vlc_ml_media_list_t * res;
+
+ if (vlc_ml_list(p_ml, VLC_ML_LIST_FOLDER_MEDIA, params, i_folder_id, &res) != VLC_SUCCESS)
+ return NULL;
+
+ return res;
+}
+
+static inline size_t vlc_ml_count_folder_media(vlc_medialibrary_t * p_ml,
+ const vlc_ml_query_params_t * params,
+ int64_t i_folder_id)
+{
+ vlc_assert(p_ml != NULL);
+
+ size_t count;
+
+ if (vlc_ml_list(p_ml, VLC_ML_COUNT_FOLDER_MEDIA, params, i_folder_id, &count) != VLC_SUCCESS)
+ return 0;
+
+ return count;
+}
+
#ifdef __cplusplus
}
#endif /* C++ */
=====================================
modules/gui/qt/Makefile.am
=====================================
@@ -162,6 +162,8 @@ libqt_plugin_la_SOURCES = \
gui/qt/medialibrary/mlbookmarkmodel.cpp \
gui/qt/medialibrary/mlbookmarkmodel.hpp \
gui/qt/medialibrary/mlevent.hpp \
+ gui/qt/medialibrary/mlfolder.cpp \
+ gui/qt/medialibrary/mlfolder.hpp \
gui/qt/medialibrary/mlfoldersmodel.cpp \
gui/qt/medialibrary/mlfoldersmodel.hpp \
gui/qt/medialibrary/mlgenre.cpp \
@@ -170,8 +172,6 @@ libqt_plugin_la_SOURCES = \
gui/qt/medialibrary/mlgenremodel.hpp \
gui/qt/medialibrary/mlgroup.cpp \
gui/qt/medialibrary/mlgroup.hpp \
- gui/qt/medialibrary/mlgrouplistmodel.cpp \
- gui/qt/medialibrary/mlgrouplistmodel.hpp \
gui/qt/medialibrary/mlhelper.cpp \
gui/qt/medialibrary/mlhelper.hpp \
gui/qt/medialibrary/mlitemcover.cpp \
@@ -191,6 +191,10 @@ libqt_plugin_la_SOURCES = \
gui/qt/medialibrary/mlurlmodel.hpp \
gui/qt/medialibrary/mlvideo.cpp \
gui/qt/medialibrary/mlvideo.hpp \
+ gui/qt/medialibrary/mlvideofoldersmodel.cpp \
+ gui/qt/medialibrary/mlvideofoldersmodel.hpp \
+ gui/qt/medialibrary/mlvideogroupsmodel.cpp \
+ gui/qt/medialibrary/mlvideogroupsmodel.hpp \
gui/qt/medialibrary/mlvideomodel.cpp \
gui/qt/medialibrary/mlvideomodel.hpp \
gui/qt/medialibrary/mlplaylist.cpp \
@@ -391,7 +395,6 @@ nodist_libqt_plugin_la_SOURCES = \
gui/qt/medialibrary/mlbasemodel.moc.cpp \
gui/qt/medialibrary/mlfoldersmodel.moc.cpp \
gui/qt/medialibrary/mlgenremodel.moc.cpp \
- gui/qt/medialibrary/mlgrouplistmodel.moc.cpp \
gui/qt/medialibrary/mllistcache.moc.cpp \
gui/qt/medialibrary/mlthreadpool.moc.cpp \
gui/qt/medialibrary/mlqmltypes.moc.cpp \
@@ -402,6 +405,8 @@ nodist_libqt_plugin_la_SOURCES = \
gui/qt/medialibrary/mlvideomodel.moc.cpp \
gui/qt/medialibrary/mlplaylistlistmodel.moc.cpp \
gui/qt/medialibrary/mlplaylistmodel.moc.cpp \
+ gui/qt/medialibrary/mlvideofoldersmodel.moc.cpp \
+ gui/qt/medialibrary/mlvideogroupsmodel.moc.cpp \
gui/qt/menus/custom_menus.moc.cpp \
gui/qt/menus/qml_menu_wrapper.moc.cpp \
gui/qt/menus/menus.moc.cpp \
=====================================
modules/gui/qt/maininterface/mainui.cpp
=====================================
@@ -13,7 +13,8 @@
#include "medialibrary/mlrecentsmodel.hpp"
#include "medialibrary/mlrecentsvideomodel.hpp"
#include "medialibrary/mlfoldersmodel.hpp"
-#include "medialibrary/mlgrouplistmodel.hpp"
+#include "medialibrary/mlvideogroupsmodel.hpp"
+#include "medialibrary/mlvideofoldersmodel.hpp"
#include "medialibrary/mlplaylistlistmodel.hpp"
#include "medialibrary/mlplaylistmodel.hpp"
#include "medialibrary/mlplaylist.hpp"
@@ -324,7 +325,8 @@ void MainUI::registerQMLTypes()
qmlRegisterType<MLUrlModel>( uri, versionMajor, versionMinor, "MLUrlModel" );
qmlRegisterType<MLVideoModel>( uri, versionMajor, versionMinor, "MLVideoModel" );
qmlRegisterType<MLRecentsVideoModel>( uri, versionMajor, versionMinor, "MLRecentsVideoModel" );
- qmlRegisterType<MLGroupListModel>( uri, versionMajor, versionMinor, "MLGroupListModel" );
+ qmlRegisterType<MLVideoGroupsModel>( uri, versionMajor, versionMinor, "MLVideoGroupsModel" );
+ qmlRegisterType<MLVideoFoldersModel>( uri, versionMajor, versionMinor, "MLVideoFoldersModel" );
qmlRegisterType<MLPlaylistListModel>( uri, versionMajor, versionMinor, "MLPlaylistListModel" );
qmlRegisterType<MLPlaylistModel>( uri, versionMajor, versionMinor, "MLPlaylistModel" );
@@ -347,7 +349,8 @@ void MainUI::registerQMLTypes()
qmlRegisterType<AlbumTrackContextMenu>( uri, versionMajor, versionMinor, "AlbumTrackContextMenu" );
qmlRegisterType<URLContextMenu>( uri, versionMajor, versionMinor, "URLContextMenu" );
qmlRegisterType<VideoContextMenu>( uri, versionMajor, versionMinor, "VideoContextMenu" );
- qmlRegisterType<GroupListContextMenu>( uri, versionMajor, versionMinor, "GroupListContextMenu" );
+ qmlRegisterType<VideoGroupsContextMenu>( uri, versionMajor, versionMinor, "VideoGroupsContextMenu" );
+ qmlRegisterType<VideoFoldersContextMenu>( uri, versionMajor, versionMinor, "VideoFoldersContextMenu" );
qmlRegisterType<PlaylistListContextMenu>( uri, versionMajor, versionMinor, "PlaylistListContextMenu" );
qmlRegisterType<PlaylistMediaContextMenu>( uri, versionMajor, versionMinor, "PlaylistMediaContextMenu" );
=====================================
modules/gui/qt/medialibrary/mlbasemodel.hpp
=====================================
@@ -36,8 +36,10 @@
#include "mlqueryparams.hpp"
#include "util/listcacheloader.hpp"
+// Fordward declarations
class MLListCache;
class MediaLib;
+class MLItemCover;
class MLBaseModel : public QAbstractListModel
{
@@ -172,6 +174,9 @@ protected:
bool m_need_reset = false;
mutable std::unique_ptr<MLListCache> m_cache;
+
+private: // Friends
+ friend QString getVideoListCover(const MLBaseModel*, MLItemCover*, int, int, int);
};
#endif // MLBASEMODEL_HPP
=====================================
modules/gui/qt/medialibrary/mlfolder.cpp
=====================================
@@ -0,0 +1,64 @@
+/*****************************************************************************
+ * Copyright (C) 2021 VLC authors and VideoLAN
+ *
+ * Authors: Benjamin Arnaud <bunjee at omega.gg>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * ( at your option ) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#include "mlfolder.hpp"
+
+// Ctor / dtor
+
+MLFolder::MLFolder(const vlc_ml_folder_t * data)
+ : MLItemCover(MLItemId(data->i_id, VLC_ML_PARENT_FOLDER))
+ , m_present(data->b_present)
+ , m_banned(data->b_banned)
+ , m_title(data->psz_name)
+ , m_mrl(data->psz_mrl)
+ , m_duration(0) // FIXME: We should have a duration field in vlc_ml_folder_t.
+ , m_count(data->i_nb_media) {}
+
+// Interface
+
+bool MLFolder::isPresent() const
+{
+ return m_present;
+}
+
+bool MLFolder::isBanned() const
+{
+ return m_banned;
+}
+
+QString MLFolder::getTitle() const
+{
+ return m_title;
+}
+
+QString MLFolder::getMRL() const
+{
+ return m_mrl;
+}
+
+int64_t MLFolder::getDuration() const
+{
+ return m_duration;
+}
+
+unsigned int MLFolder::getCount() const
+{
+ return m_count;
+}
=====================================
modules/gui/qt/medialibrary/mlfolder.hpp
=====================================
@@ -0,0 +1,57 @@
+/*****************************************************************************
+ * Copyright (C) 2021 VLC authors and VideoLAN
+ *
+ * Authors: Benjamin Arnaud <bunjee at omega.gg>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * ( at your option ) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#ifndef MLFOLDER_HPP
+#define MLFOLDER_HPP
+
+// MediaLibrary includes
+#include "mlitemcover.hpp"
+
+class MLFolder : public MLItemCover
+{
+public:
+ MLFolder(const vlc_ml_folder_t * data);
+
+public: // Interface
+ bool isPresent() const;
+ bool isBanned() const;
+
+ QString getTitle() const;
+
+ QString getMRL() const;
+
+ int64_t getDuration() const;
+
+ unsigned int getCount() const;
+
+private:
+ bool m_present;
+ bool m_banned;
+
+ QString m_title;
+
+ QString m_mrl;
+
+ int64_t m_duration;
+
+ unsigned int m_count;
+};
+
+#endif
=====================================
modules/gui/qt/medialibrary/mlhelper.cpp
=====================================
@@ -18,6 +18,10 @@
#include "mlhelper.hpp"
+// MediaLibrary includes
+#include "mlbasemodel.hpp"
+#include "mlitemcover.hpp"
+
QString MsToString( int64_t time , bool doShort )
{
if (time < 0)
@@ -42,3 +46,59 @@ QString MsToString( int64_t time , bool doShort )
.arg(sec, 2, 10, QChar('0'));
}
+
+QString getVideoListCover( const MLBaseModel* model, MLItemCover* item, int width, int height,
+ int role )
+{
+ QString cover = item->getCover();
+
+ // NOTE: Making sure we're not already generating a cover.
+ if (cover.isNull() == false || item->hasGenerator())
+ return cover;
+
+ MLItemId itemId = item->getId();
+
+ struct Context { QString cover; };
+
+ item->setGenerator(true);
+
+ model->ml()->runOnMLThread<Context>(model,
+ //ML thread
+ [itemId, width, height]
+ (vlc_medialibrary_t * ml, Context & ctx)
+ {
+ CoverGenerator generator{ ml, itemId };
+
+ generator.setSize(QSize(width, height));
+
+ generator.setDefaultThumbnail(":/noart_videoCover.svg");
+
+ if (generator.cachedFileAvailable())
+ ctx.cover = generator.cachedFileURL();
+ else
+ ctx.cover = generator.execute();
+ },
+ //UI Thread
+ [model, itemId, role]
+ (quint64, Context & ctx)
+ {
+ int row;
+
+ // NOTE: We want to avoid calling 'MLBaseModel::item' for performance issues.
+ auto item = static_cast<MLItemCover *>(model->findInCache(itemId, &row));
+
+ if (!item)
+ return;
+
+ item->setCover(ctx.cover);
+
+ item->setGenerator(false);
+
+ QModelIndex modelIndex = model->index(row);
+
+ //we're running in a callback
+ emit const_cast<MLBaseModel *>(model)->dataChanged(modelIndex, modelIndex, { role });
+ });
+
+ return cover;
+}
=====================================
modules/gui/qt/medialibrary/mlhelper.hpp
=====================================
@@ -28,6 +28,10 @@
#include "vlc_media_library.h"
#include <QString>
+// Forward declarations
+class MLBaseModel;
+class MLItemCover;
+
template<typename T>
class MLDeleter
{
@@ -73,4 +77,7 @@ MLListRange<T> ml_range_iterate(L& list)
QString MsToString( int64_t time, bool doShort = false );
+QString getVideoListCover( const MLBaseModel* model, MLItemCover* item, int width, int height,
+ int role );
+
#endif // MLHELPER_HPP
=====================================
modules/gui/qt/medialibrary/mlqmltypes.hpp
=====================================
@@ -53,6 +53,7 @@ public:
ML_PARENT_TYPE_CASE(VLC_ML_PARENT_SHOW);
ML_PARENT_TYPE_CASE(VLC_ML_PARENT_GENRE);
ML_PARENT_TYPE_CASE(VLC_ML_PARENT_GROUP);
+ ML_PARENT_TYPE_CASE(VLC_ML_PARENT_FOLDER);
ML_PARENT_TYPE_CASE(VLC_ML_PARENT_PLAYLIST);
default:
return QString("UNKNOWN - %2").arg(id);
=====================================
modules/gui/qt/medialibrary/mlvideofoldersmodel.cpp
=====================================
@@ -0,0 +1,169 @@
+/*****************************************************************************
+ * Copyright (C) 2021 VLC authors and VideoLAN
+ *
+ * Authors: Benjamin Arnaud <bunjee at omega.gg>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * ( at your option ) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include "mlvideofoldersmodel.hpp"
+
+// VLC includes
+#include <vlc_media_library.h>
+
+// Util includes
+#include "util/covergenerator.hpp"
+
+// MediaLibrary includes
+#include "mlhelper.hpp"
+#include "mlfolder.hpp"
+
+// Static variables
+
+// NOTE: We multiply by 2 to cover most dpi settings.
+static const int MLVIDEOFOLDERSMODEL_COVER_WIDTH = 512 * 2; // 16 / 10 ratio
+static const int MLVIDEOFOLDERSMODEL_COVER_HEIGHT = 320 * 2;
+
+static const QHash<QByteArray, vlc_ml_sorting_criteria_t> criterias =
+{
+ { "title", VLC_ML_SORTING_ALPHA },
+ { "duration", VLC_ML_SORTING_DURATION }
+};
+
+// Ctor / dtor
+
+/* explicit */ MLVideoFoldersModel::MLVideoFoldersModel(QObject * parent) : MLBaseModel(parent) {}
+
+// MLBaseModel reimplementation
+
+QHash<int, QByteArray> MLVideoFoldersModel::roleNames() const /* override */
+{
+ return {
+ { FOLDER_ID, "id" },
+ { FOLDER_IS_NEW, "isNew" },
+ { FOLDER_TITLE, "title" },
+ { FOLDER_THUMBNAIL, "thumbnail" },
+ { FOLDER_DURATION, "duration" },
+ { FOLDER_PROGRESS, "progress" },
+ { FOLDER_COUNT, "count"},
+ };
+}
+
+// Protected MLVideoModel implementation
+
+QVariant MLVideoFoldersModel::itemRoleData(MLItem * item, const int role) const /* override */
+{
+ if (item == nullptr)
+ return QVariant();
+
+ MLFolder * folder = static_cast<MLFolder *> (item);
+
+ switch (role)
+ {
+ // NOTE: This is the condition for QWidget view(s).
+ case Qt::DisplayRole:
+ return QVariant::fromValue(folder->getTitle());
+ // NOTE: These are the conditions for QML view(s).
+ case FOLDER_ID:
+ return QVariant::fromValue(folder->getId());
+ case FOLDER_TITLE:
+ return QVariant::fromValue(folder->getTitle());
+ case FOLDER_THUMBNAIL:
+ return getVideoListCover(this, folder, MLVIDEOFOLDERSMODEL_COVER_WIDTH,
+ MLVIDEOFOLDERSMODEL_COVER_HEIGHT, FOLDER_THUMBNAIL);
+ case FOLDER_DURATION:
+ return QVariant::fromValue(folder->getDuration());
+ case FOLDER_COUNT:
+ return QVariant::fromValue(folder->getCount());
+ default:
+ return QVariant();
+ }
+}
+
+vlc_ml_sorting_criteria_t MLVideoFoldersModel::roleToCriteria(int role) const /* override */
+{
+ switch (role)
+ {
+ case FOLDER_TITLE:
+ return VLC_ML_SORTING_ALPHA;
+ case FOLDER_DURATION:
+ return VLC_ML_SORTING_DURATION;
+ default:
+ return VLC_ML_SORTING_DEFAULT;
+ }
+}
+
+vlc_ml_sorting_criteria_t MLVideoFoldersModel::nameToCriteria(QByteArray name) const /* override */
+{
+ return criterias.value(name, VLC_ML_SORTING_DEFAULT);
+}
+
+QByteArray MLVideoFoldersModel::criteriaToName(vlc_ml_sorting_criteria_t criteria) const
+/* override */
+{
+ return criterias.key(criteria, "");
+}
+
+ListCacheLoader<std::unique_ptr<MLItem>> * MLVideoFoldersModel::createLoader() const /* override */
+{
+ return new Loader(*this);
+}
+
+// Protected MLBaseModel reimplementation
+
+void MLVideoFoldersModel::onVlcMlEvent(const MLEvent & event) /* override */
+{
+ // FIXME: Add support for folder events once the MediaLibrary supports them.
+
+ MLBaseModel::onVlcMlEvent(event);
+}
+
+// Loader
+
+MLVideoFoldersModel::Loader::Loader(const MLVideoFoldersModel & model)
+ : MLBaseModel::BaseLoader(model) {}
+
+size_t MLVideoFoldersModel::Loader::count(vlc_medialibrary_t * ml) const /* override */
+{
+ vlc_ml_query_params_t params = getParams().toCQueryParams();
+
+ return vlc_ml_count_folders_by_type(ml, ¶ms, VLC_ML_MEDIA_TYPE_VIDEO);
+}
+
+std::vector<std::unique_ptr<MLItem>>
+MLVideoFoldersModel::Loader::load(vlc_medialibrary_t * ml,
+ size_t index, size_t count) const /* override */
+{
+ vlc_ml_query_params_t params = getParams(index, count).toCQueryParams();
+
+ ml_unique_ptr<vlc_ml_folder_list_t> list(vlc_ml_list_folders_by_type(ml, ¶ms,
+ VLC_ML_MEDIA_TYPE_VIDEO));
+
+ if (list == nullptr)
+ return {};
+
+ std::vector<std::unique_ptr<MLItem>> result;
+
+ for (const vlc_ml_folder_t & folder : ml_range_iterate<vlc_ml_folder_t>(list))
+ {
+ result.emplace_back(std::make_unique<MLFolder>(&folder));
+ }
+
+ return result;
+}
=====================================
modules/gui/qt/medialibrary/mlvideofoldersmodel.hpp
=====================================
@@ -0,0 +1,78 @@
+/*****************************************************************************
+ * Copyright (C) 2021 VLC authors and VideoLAN
+ *
+ * Authors: Benjamin Arnaud <bunjee at omega.gg>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * ( at your option ) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#ifndef MLVIDEOFOLDERSMODEL_HPP
+#define MLVIDEOFOLDERSMODEL_HPP
+
+// MediaLibrary includes
+#include "mlvideomodel.hpp"
+
+// Forward declarations
+class MLFolder;
+
+class MLVideoFoldersModel : public MLBaseModel
+{
+ Q_OBJECT
+
+public:
+ enum Roles
+ {
+ FOLDER_ID = Qt::UserRole + 1,
+ FOLDER_IS_NEW,
+ FOLDER_TITLE,
+ FOLDER_THUMBNAIL,
+ FOLDER_DURATION,
+ FOLDER_PROGRESS,
+ FOLDER_COUNT
+ };
+
+public:
+ explicit MLVideoFoldersModel(QObject * parent = nullptr);
+
+public: // MLBaseModel reimplementation
+ QHash<int, QByteArray> roleNames() const override;
+
+protected:
+ QVariant itemRoleData(MLItem *item, int role = Qt::DisplayRole) const override;
+
+ vlc_ml_sorting_criteria_t roleToCriteria(int role) const override;
+
+ vlc_ml_sorting_criteria_t nameToCriteria(QByteArray name) const override;
+
+ QByteArray criteriaToName(vlc_ml_sorting_criteria_t criteria) const override;
+
+ ListCacheLoader<std::unique_ptr<MLItem>> * createLoader() const override;
+
+protected: // MLBaseModel reimplementation
+ void onVlcMlEvent(const MLEvent & event) override;
+
+private:
+ struct Loader : public BaseLoader
+ {
+ Loader(const MLVideoFoldersModel & model);
+
+ size_t count(vlc_medialibrary_t * ml) const override;
+
+ std::vector<std::unique_ptr<MLItem>> load(vlc_medialibrary_t * ml,
+ size_t index, size_t count) const override;
+ };
+};
+
+#endif // MLVIDEOFOLDERSMODEL_HPP
=====================================
modules/gui/qt/medialibrary/mlgrouplistmodel.cpp → modules/gui/qt/medialibrary/mlvideogroupsmodel.cpp
=====================================
@@ -22,7 +22,7 @@
# include "config.h"
#endif
-#include "mlgrouplistmodel.hpp"
+#include "mlvideogroupsmodel.hpp"
// VLC includes
#include <vlc_media_library.h>
@@ -39,8 +39,8 @@
// Static variables
// NOTE: We multiply by 2 to cover most dpi settings.
-static const int MLGROUPLISTMODEL_COVER_WIDTH = 512 * 2; // 16 / 10 ratio
-static const int MLGROUPLISTMODEL_COVER_HEIGHT = 320 * 2;
+static const int MLVIDEOGROUPSMODEL_COVER_WIDTH = 512 * 2; // 16 / 10 ratio
+static const int MLVIDEOGROUPSMODEL_COVER_HEIGHT = 320 * 2;
static const QHash<QByteArray, vlc_ml_sorting_criteria_t> criterias =
{
@@ -50,43 +50,29 @@ static const QHash<QByteArray, vlc_ml_sorting_criteria_t> criterias =
};
//=================================================================================================
-// MLGroupListModel
+// MLVideoGroupsModel
//=================================================================================================
-/* explicit */ MLGroupListModel::MLGroupListModel(QObject * parent)
- : MLBaseModel(parent) {}
+/* explicit */ MLVideoGroupsModel::MLVideoGroupsModel(QObject * parent) : MLVideoModel(parent) {}
//-------------------------------------------------------------------------------------------------
-// QAbstractItemModel implementation
+// MLVideoModel reimplementation
//-------------------------------------------------------------------------------------------------
-QHash<int, QByteArray> MLGroupListModel::roleNames() const /* override */
+QHash<int, QByteArray> MLVideoGroupsModel::roleNames() const /* override */
{
- return
- {
- { GROUP_IS_VIDEO, "isVideo" },
- { GROUP_ID, "id" },
- { GROUP_TITLE, "title" },
- { GROUP_THUMBNAIL, "thumbnail" },
- { GROUP_DURATION, "duration" },
- { GROUP_DATE, "date" },
- { GROUP_COUNT, "count" },
- // NOTE: Media specific.
- { GROUP_IS_NEW, "isNew" },
- { GROUP_FILENAME, "fileName" },
- { GROUP_PROGRESS, "progress" },
- { GROUP_PLAYCOUNT, "playcount" },
- { GROUP_RESOLUTION, "resolution_name" },
- { GROUP_CHANNEL, "channel" },
- { GROUP_MRL, "mrl" },
- { GROUP_MRL_DISPLAY, "display_mrl" },
- { GROUP_VIDEO_TRACK, "videoDesc" },
- { GROUP_AUDIO_TRACK, "audioDesc" },
- { GROUP_TITLE_FIRST_SYMBOL, "title_first_symbol" }
- };
+ QHash<int, QByteArray> hash = MLVideoModel::roleNames();
+
+ hash.insert(GROUP_IS_VIDEO, "isVideo");
+ hash.insert(GROUP_DATE, "date");
+ hash.insert(GROUP_COUNT, "count");
+
+ return hash;
}
-QVariant MLGroupListModel::itemRoleData(MLItem *item, const int role) const /* override */
+// Protected MLVideoModel implementation
+
+QVariant MLVideoGroupsModel::itemRoleData(MLItem * item, const int role) const /* override */
{
if (item == nullptr)
return QVariant();
@@ -101,16 +87,17 @@ QVariant MLGroupListModel::itemRoleData(MLItem *item, const int role) const /* o
case Qt::DisplayRole:
return QVariant::fromValue(group->getTitle());
// NOTE: These are the conditions for QML view(s).
- case GROUP_IS_VIDEO:
- return false;
- case GROUP_ID:
+ case VIDEO_ID:
return QVariant::fromValue(group->getId());
- case GROUP_TITLE:
+ case VIDEO_TITLE:
return QVariant::fromValue(group->getTitle());
- case GROUP_THUMBNAIL:
- return getCover(group);
- case GROUP_DURATION:
+ case VIDEO_THUMBNAIL:
+ return getVideoListCover(this, group, MLVIDEOGROUPSMODEL_COVER_WIDTH,
+ MLVIDEOGROUPSMODEL_COVER_HEIGHT, VIDEO_THUMBNAIL);
+ case VIDEO_DURATION:
return QVariant::fromValue(group->getDuration());
+ case GROUP_IS_VIDEO:
+ return false;
case GROUP_DATE:
return QVariant::fromValue(group->getDate());
case GROUP_COUNT:
@@ -129,66 +116,24 @@ QVariant MLGroupListModel::itemRoleData(MLItem *item, const int role) const /* o
return QVariant::fromValue(video->getTitle());
case GROUP_IS_VIDEO:
return true;
- case GROUP_ID:
- return QVariant::fromValue(video->getId());
- case GROUP_TITLE:
- return QVariant::fromValue(video->getTitle());
- case GROUP_THUMBNAIL:
- {
- vlc_ml_thumbnail_status_t status;
- const QString thumbnail = video->getThumbnail(&status);
- if (status == VLC_ML_THUMBNAIL_STATUS_MISSING || status == VLC_ML_THUMBNAIL_STATUS_FAILURE)
- {
- generateVideoThumbnail(item->getId().id);
- }
- return QVariant::fromValue( thumbnail );
- }
- case GROUP_DURATION:
- return QVariant::fromValue(video->getDuration());
case GROUP_DATE:
return QVariant();
case GROUP_COUNT:
return 1;
// NOTE: Media specific.
- case GROUP_IS_NEW:
- return QVariant::fromValue(video->isNew());
- case GROUP_FILENAME:
- return QVariant::fromValue(video->getFileName());
- case GROUP_PROGRESS:
- return QVariant::fromValue(video->getProgress());
- case GROUP_PLAYCOUNT:
- return QVariant::fromValue(video->getPlayCount());
- case GROUP_RESOLUTION:
- return QVariant::fromValue(video->getResolutionName());
- case GROUP_CHANNEL:
- return QVariant::fromValue(video->getChannel());
- case GROUP_MRL:
- return QVariant::fromValue(video->getMRL());
- case GROUP_MRL_DISPLAY:
- return QVariant::fromValue(video->getDisplayMRL());
- case GROUP_VIDEO_TRACK:
- return QVariant::fromValue(video->getVideoDesc());
- case GROUP_AUDIO_TRACK:
- return QVariant::fromValue(video->getAudioDesc());
- case GROUP_TITLE_FIRST_SYMBOL:
- return QVariant::fromValue(getFirstSymbol(video->getTitle()));
default:
- return QVariant();
+ return MLVideoModel::itemRoleData(item, role);
}
}
}
-//-------------------------------------------------------------------------------------------------
-// Protected MLBaseModel implementation
-//-------------------------------------------------------------------------------------------------
-
-vlc_ml_sorting_criteria_t MLGroupListModel::roleToCriteria(int role) const /* override */
+vlc_ml_sorting_criteria_t MLVideoGroupsModel::roleToCriteria(int role) const /* override */
{
switch (role)
{
- case GROUP_TITLE:
+ case VIDEO_TITLE:
return VLC_ML_SORTING_ALPHA;
- case GROUP_DURATION:
+ case VIDEO_DURATION:
return VLC_ML_SORTING_DURATION;
case GROUP_DATE:
return VLC_ML_SORTING_INSERTIONDATE;
@@ -197,93 +142,23 @@ vlc_ml_sorting_criteria_t MLGroupListModel::roleToCriteria(int role) const /* ov
}
}
-vlc_ml_sorting_criteria_t MLGroupListModel::nameToCriteria(QByteArray name) const /* override */
+vlc_ml_sorting_criteria_t MLVideoGroupsModel::nameToCriteria(QByteArray name) const /* override */
{
return criterias.value(name, VLC_ML_SORTING_DEFAULT);
}
-QByteArray MLGroupListModel::criteriaToName(vlc_ml_sorting_criteria_t criteria) const
+QByteArray MLVideoGroupsModel::criteriaToName(vlc_ml_sorting_criteria_t criteria) const
/* override */
{
return criterias.key(criteria, "");
}
-//-------------------------------------------------------------------------------------------------
-
-ListCacheLoader<std::unique_ptr<MLItem>> * MLGroupListModel::createLoader() const /* override */
+ListCacheLoader<std::unique_ptr<MLItem>> * MLVideoGroupsModel::createLoader() const /* override */
{
return new Loader(*this);
}
-//-------------------------------------------------------------------------------------------------
-// Private functions
-//-------------------------------------------------------------------------------------------------
-
-QString MLGroupListModel::getCover(MLGroup * group) const
-{
- QString cover = group->getCover();
-
- // NOTE: Making sure we're not already generating a cover.
- if (cover.isNull() == false || group->hasGenerator())
- return cover;
-
- MLItemId groupId = group->getId();
- struct Context{
- QString cover;
- };
- group->setGenerator(true);
- m_mediaLib->runOnMLThread<Context>(this,
- //ML thread
- [groupId]
- (vlc_medialibrary_t* ml, Context& ctx){
- CoverGenerator generator{ml, groupId};
-
- generator.setSize(QSize(MLGROUPLISTMODEL_COVER_WIDTH,
- MLGROUPLISTMODEL_COVER_HEIGHT));
-
- generator.setDefaultThumbnail(":/noart_videoCover.svg");
-
- if (generator.cachedFileAvailable())
- ctx.cover = generator.cachedFileURL();
- else
- ctx.cover = generator.execute();
- },
- //UI Thread
- [this, groupId]
- (quint64, Context& ctx)
- {
- int row;
- // NOTE: We want to avoid calling 'MLBaseModel::item' for performance issues.
- auto group = static_cast<MLGroup*>(findInCache(groupId, &row));
- if (!group)
- return;
-
- group->setCover(ctx.cover);
- group->setGenerator(false);
-
- QModelIndex modelIndex =this->index(row);
- //we're running in a callback
- emit const_cast<MLGroupListModel*>(this)->dataChanged(modelIndex, modelIndex, { GROUP_THUMBNAIL });
- });
-
- return cover;
-}
-
-
-void MLGroupListModel::generateVideoThumbnail(uint64_t id) const
-{
- m_mediaLib->runOnMLThread(this,
- //ML thread
- [id](vlc_medialibrary_t* ml){
- vlc_ml_media_generate_thumbnail(ml, id, VLC_ML_THUMBNAIL_SMALL, 512, 320, .15 );
- });
-}
-
-//-------------------------------------------------------------------------------------------------
-// Private MLBaseModel reimplementation
-//-------------------------------------------------------------------------------------------------
-
-void MLGroupListModel::onVlcMlEvent(const MLEvent & event) /* override */
+void MLVideoGroupsModel::onVlcMlEvent(const MLEvent & event) /* override */
{
int type = event.i_type;
@@ -306,22 +181,14 @@ void MLGroupListModel::onVlcMlEvent(const MLEvent & event) /* override */
MLBaseModel::onVlcMlEvent(event);
}
-void MLGroupListModel::thumbnailUpdated(const QModelIndex& idx, MLItem* mlitem, const QString& mrl, vlc_ml_thumbnail_status_t status) /* override */
-{
- auto videoItem = static_cast<MLVideo*>(mlitem);
- videoItem->setThumbnail(status, mrl);
- emit dataChanged(idx, idx, { GROUP_THUMBNAIL });
-}
-
-
//=================================================================================================
// Loader
//=================================================================================================
-MLGroupListModel::Loader::Loader(const MLGroupListModel & model)
+MLVideoGroupsModel::Loader::Loader(const MLVideoGroupsModel & model)
: MLBaseModel::BaseLoader(model) {}
-size_t MLGroupListModel::Loader::count(vlc_medialibrary_t* ml) const /* override */
+size_t MLVideoGroupsModel::Loader::count(vlc_medialibrary_t* ml) const /* override */
{
vlc_ml_query_params_t params = getParams().toCQueryParams();
@@ -329,7 +196,8 @@ size_t MLGroupListModel::Loader::count(vlc_medialibrary_t* ml) const /* override
}
std::vector<std::unique_ptr<MLItem>>
-MLGroupListModel::Loader::load(vlc_medialibrary_t* ml, size_t index, size_t count) const /* override */
+MLVideoGroupsModel::Loader::load(vlc_medialibrary_t* ml,
+ size_t index, size_t count) const /* override */
{
vlc_ml_query_params_t params = getParams(index, count).toCQueryParams();
=====================================
modules/gui/qt/medialibrary/mlgrouplistmodel.hpp → modules/gui/qt/medialibrary/mlvideogroupsmodel.hpp
=====================================
@@ -18,53 +18,35 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
*****************************************************************************/
-#ifndef MLGROUPLISTMODEL_HPP
-#define MLGROUPLISTMODEL_HPP
+#ifndef MLVIDEOGROUPSMODEL_HPP
+#define MLVIDEOGROUPSMODEL_HPP
// MediaLibrary includes
-#include "mlbasemodel.hpp"
+#include "mlvideomodel.hpp"
// Forward declarations
-struct vlc_medialibrary_t;
class MLGroup;
-class MLGroupListModel : public MLBaseModel
+class MLVideoGroupsModel : public MLVideoModel
{
Q_OBJECT
public:
enum Roles
{
- GROUP_IS_VIDEO = Qt::UserRole + 1,
- GROUP_ID,
- GROUP_TITLE,
- GROUP_THUMBNAIL,
- GROUP_DURATION,
+ // NOTE: Group specific.
+ GROUP_IS_VIDEO = VIDEO_TITLE_FIRST_SYMBOL + 1,
GROUP_DATE,
- GROUP_COUNT,
- // NOTE: Media specific.
- GROUP_IS_NEW,
- GROUP_FILENAME,
- GROUP_PROGRESS,
- GROUP_PLAYCOUNT,
- GROUP_RESOLUTION,
- GROUP_CHANNEL,
- GROUP_MRL,
- GROUP_MRL_DISPLAY,
- GROUP_VIDEO_TRACK,
- GROUP_AUDIO_TRACK,
-
- GROUP_TITLE_FIRST_SYMBOL
+ GROUP_COUNT
};
public:
- explicit MLGroupListModel(QObject * parent = nullptr);
+ explicit MLVideoGroupsModel(QObject * parent = nullptr);
-
-public: // QAbstractItemModel implementation
+public: // MLVideoModel reimplementation
QHash<int, QByteArray> roleNames() const override;
-protected: // MLBaseModel implementation
+protected: // MLVideoModel reimplementation
QVariant itemRoleData(MLItem *item, int role = Qt::DisplayRole) const override;
vlc_ml_sorting_criteria_t roleToCriteria(int role) const override;
@@ -75,20 +57,12 @@ protected: // MLBaseModel implementation
ListCacheLoader<std::unique_ptr<MLItem>> * createLoader() const override;
- void thumbnailUpdated(const QModelIndex& idx, MLItem* mlitem, const QString& mrl, vlc_ml_thumbnail_status_t status) override;
-
-private: // Functions
- QString getCover(MLGroup * group) const;
-
-private: // MLBaseModel implementation
void onVlcMlEvent(const MLEvent & event) override;
- void generateVideoThumbnail(uint64_t id) const;
-
private:
- struct Loader : public MLBaseModel::BaseLoader
+ struct Loader : public BaseLoader
{
- Loader(const MLGroupListModel & model);
+ Loader(const MLVideoGroupsModel & model);
size_t count(vlc_medialibrary_t* ml) const override;
@@ -96,4 +70,4 @@ private:
};
};
-#endif // MLGROUPLISTMODEL_HPP
+#endif // MLVIDEOGROUPSMODEL_HPP
=====================================
modules/gui/qt/medialibrary/mlvideomodel.cpp
=====================================
@@ -188,7 +188,7 @@ size_t MLVideoModel::Loader::count(vlc_medialibrary_t* ml) const /* override */
if (id <= 0)
return vlc_ml_count_video_media(ml, ¶ms);
else
- return vlc_ml_count_media_of(ml, ¶ms, m_parent.type, id);
+ return vlc_ml_count_video_of(ml, ¶ms, m_parent.type, id);
}
std::vector<std::unique_ptr<MLItem>>
@@ -203,7 +203,7 @@ MLVideoModel::Loader::load(vlc_medialibrary_t* ml, size_t index, size_t count) c
if (id <= 0)
list.reset(vlc_ml_list_video_media(ml, ¶ms));
else
- list.reset(vlc_ml_list_media_of(ml, ¶ms, m_parent.type, id));
+ list.reset(vlc_ml_list_video_of(ml, ¶ms, m_parent.type, id));
if (list == nullptr)
return {};
=====================================
modules/gui/qt/medialibrary/qml/MediaGroupDisplay.qml
=====================================
@@ -32,7 +32,7 @@ VideoAll {
property int initialIndex: 0
property MLItemId initialId
- property string initialName
+ property string initialTitle
// Aliases
=====================================
modules/gui/qt/medialibrary/qml/VideoAllSubDisplay.qml
=====================================
@@ -40,8 +40,16 @@ VideoAll {
// Private
- property var _meta: (MainCtx.grouping === MainCtx.GROUPING_NONE) ? metaVideo
- : metaGroup
+ property var _meta: {
+ var grouping = MainCtx.grouping;
+
+ if (grouping === MainCtx.GROUPING_NONE)
+ return metaVideo
+ else if (grouping === MainCtx.GROUPING_NAME)
+ return metaGroup
+ else if (grouping === MainCtx.GROUPING_FOLDER)
+ return metaFolder
+ }
// Signals
@@ -114,9 +122,9 @@ VideoAll {
QtObject {
id: metaGroup
- property var model: MLGroupListModel { ml: MediaLib }
+ property var model: MLVideoGroupsModel { ml: MediaLib }
- property var contextMenu: GroupListContextMenu { model: metaGroup.model }
+ property var contextMenu: VideoGroupsContextMenu { model: metaGroup.model }
function onAction(indexes) {
var index = indexes[0]
@@ -153,6 +161,32 @@ VideoAll {
}
}
+ QtObject {
+ id: metaFolder
+
+ property var model: MLVideoFoldersModel { ml: MediaLib }
+
+ property var contextMenu: VideoFoldersContextMenu { model: metaFolder.model }
+
+ function onAction(indexes) {
+ var index = indexes[0]
+
+ root.showList(model.getDataAt(index), Qt.TabFocusReason)
+ }
+
+ function onDoubleClick(object) {
+ root.showList(object, Qt.MouseFocusReason)
+ }
+
+ function onLabelGrid(object) {
+ return root.getLabelGroup(object, I18n.qtr("%1 Videos"))
+ }
+
+ function onLabelList(object) {
+ return root.getLabelGroup(object, I18n.qtr("%1"))
+ }
+ }
+
// Children
MLRecentsVideoModel {
=====================================
modules/gui/qt/menus/qml_menu_wrapper.cpp
=====================================
@@ -19,7 +19,8 @@
#include "menus.hpp"
#include "medialibrary/medialib.hpp"
#include "medialibrary/mlvideomodel.hpp"
-#include "medialibrary/mlgrouplistmodel.hpp"
+#include "medialibrary/mlvideogroupsmodel.hpp"
+#include "medialibrary/mlvideofoldersmodel.hpp"
#include "medialibrary/mlplaylistlistmodel.hpp"
#include "medialibrary/mlplaylistmodel.hpp"
#include "medialibrary/mlalbummodel.hpp"
@@ -162,6 +163,7 @@ void SortMenuVideo::onPopup(QMenu * menu) /* override */
{
{ N_("Do not group videos"), MainCtx::GROUPING_NONE },
{ N_("Group by name"), MainCtx::GROUPING_NAME },
+ { N_("Group by folder"), MainCtx::GROUPING_FOLDER },
};
QActionGroup * group = new QActionGroup(this);
@@ -542,18 +544,19 @@ void VideoContextMenu::popup(const QModelIndexList& selected, QPoint pos, QVaria
}
//=================================================================================================
-// GroupListContextMenu
+// VideoGroupsContextMenu
//=================================================================================================
-GroupListContextMenu::GroupListContextMenu(QObject * parent) : QObject(parent) {}
+VideoGroupsContextMenu::VideoGroupsContextMenu(QObject * parent) : QObject(parent) {}
-GroupListContextMenu::~GroupListContextMenu() /* override */
+VideoGroupsContextMenu::~VideoGroupsContextMenu() /* override */
{
if (m_menu)
delete m_menu;
}
-void GroupListContextMenu::popup(const QModelIndexList & selected, QPoint pos, QVariantMap options)
+void VideoGroupsContextMenu::popup(const QModelIndexList & selected, QPoint pos,
+ QVariantMap options)
{
if (m_model == nullptr)
return;
@@ -564,7 +567,7 @@ void GroupListContextMenu::popup(const QModelIndexList & selected, QPoint pos, Q
QVariantList ids;
for (const QModelIndex & index : selected)
- ids.push_back(m_model->data(index, MLGroupListModel::GROUP_ID));
+ ids.push_back(m_model->data(index, MLVideoModel::VIDEO_ID));
m_menu = new QMenu();
@@ -605,7 +608,7 @@ void GroupListContextMenu::popup(const QModelIndexList & selected, QPoint pos, Q
// NOTE: At the moment informations are only available for single video(s).
if (selected.count() == 1
&&
- m_model->data(selected.first(), MLGroupListModel::GROUP_IS_VIDEO) == true
+ m_model->data(selected.first(), MLVideoGroupsModel::GROUP_IS_VIDEO) == true
&&
options.contains("information") && options["information"].type() == QVariant::Int)
{
@@ -619,16 +622,79 @@ void GroupListContextMenu::popup(const QModelIndexList & selected, QPoint pos, Q
#if QT_VERSION >= QT_VERSION_CHECK(5,15,0)
connect(mapper, &QSignalMapper::mappedInt,
- this, &GroupListContextMenu::showMediaInformation);
+ this, &VideoGroupsContextMenu::showMediaInformation);
#else
connect(mapper, QOverload<int>::of(&QSignalMapper::mapped),
- this, &GroupListContextMenu::showMediaInformation);
+ this, &VideoGroupsContextMenu::showMediaInformation);
#endif
}
m_menu->popup(pos);
}
+// VideoFoldersContextMenu
+
+VideoFoldersContextMenu::VideoFoldersContextMenu(QObject * parent) : QObject(parent) {}
+
+VideoFoldersContextMenu::~VideoFoldersContextMenu() /* override */
+{
+ if (m_menu)
+ delete m_menu;
+}
+
+void VideoFoldersContextMenu::popup(const QModelIndexList & selected, QPoint pos,
+ QVariantMap options)
+{
+ if (m_model == nullptr)
+ return;
+
+ if (m_menu)
+ delete m_menu;
+
+ QVariantList ids;
+
+ for (const QModelIndex & index : selected)
+ ids.push_back(m_model->data(index, MLVideoFoldersModel::FOLDER_ID));
+
+ m_menu = new QMenu();
+
+ MediaLib * ml = m_model->ml();
+
+ QAction * action = m_menu->addAction(qtr("Add and play"));
+
+ connect(action, &QAction::triggered, [ml, ids, options]()
+ {
+ ml->addAndPlay(ids, options["player-options"].toStringList());
+ });
+
+ action = m_menu->addAction(qtr("Enqueue"));
+
+ connect(action, &QAction::triggered, [ml, ids]()
+ {
+ ml->addToPlaylist(ids);
+ });
+
+ action = m_menu->addAction(qtr("Add to playlist"));
+
+ connect(action, &QAction::triggered, [ids]()
+ {
+ DialogsProvider::getInstance()->playlistsDialog(ids);
+ });
+
+ action = m_menu->addAction(qtr("Play as audio"));
+
+ connect(action, &QAction::triggered, [ml, ids, options]()
+ {
+ QStringList list = options["player-options"].toStringList();
+
+ list.prepend(":no-video");
+
+ ml->addAndPlay(ids, list);
+ });
+
+ m_menu->popup(pos);
+}
+
//=================================================================================================
// PlaylistListContextMenu
//=================================================================================================
=====================================
modules/gui/qt/menus/qml_menu_wrapper.hpp
=====================================
@@ -33,8 +33,8 @@ class MLArtistModel;
class MLAlbumTrackModel;
class MLUrlModel;
class MLVideoModel;
-class MLGroupListModel;
-class MLGroupModel;
+class MLVideoGroupsModel;
+class MLVideoFoldersModel;
class MLPlaylistListModel;
class MLPlaylistModel;
class NetworkDeviceModel;
@@ -278,15 +278,15 @@ private:
// Groups
//-------------------------------------------------------------------------------------------------
-class GroupListContextMenu : public QObject {
+class VideoGroupsContextMenu : public QObject {
Q_OBJECT
- SIMPLE_MENU_PROPERTY(MLGroupListModel *, model, nullptr)
+ SIMPLE_MENU_PROPERTY(MLVideoGroupsModel *, model, nullptr)
public:
- GroupListContextMenu(QObject * parent = nullptr);
+ VideoGroupsContextMenu(QObject * parent = nullptr);
- ~GroupListContextMenu() /* override */;
+ ~VideoGroupsContextMenu(); /* override */
public slots:
void popup(const QModelIndexList & selected, QPoint pos, QVariantMap options = {});
@@ -298,6 +298,29 @@ private:
QMenu * m_menu = nullptr;
};
+// Folders
+
+class VideoFoldersContextMenu : public QObject {
+ Q_OBJECT
+
+ SIMPLE_MENU_PROPERTY(MLVideoFoldersModel *, model, nullptr)
+
+public:
+ VideoFoldersContextMenu(QObject * parent = nullptr);
+
+ ~VideoFoldersContextMenu(); /* override */
+
+public slots:
+ void popup(const QModelIndexList & selected, QPoint pos, QVariantMap options = {});
+
+signals:
+ // FIXME: This signal is required for VideoAll Connections.
+ void showMediaInformation(int index);
+
+private:
+ QMenu * m_menu = nullptr;
+};
+
//-------------------------------------------------------------------------------------------------
class PlaylistListContextMenu : public QObject {
=====================================
modules/gui/qt/util/covergenerator.cpp
=====================================
@@ -357,6 +357,8 @@ QString CoverGenerator::getPrefix(vlc_ml_parent_type type) const
return "genre";
case VLC_ML_PARENT_GROUP:
return "group";
+ case VLC_ML_PARENT_FOLDER:
+ return "folder";
case VLC_ML_PARENT_PLAYLIST:
return "playlist";
default:
=====================================
modules/misc/medialibrary/entities.cpp
=====================================
@@ -455,18 +455,28 @@ bool Convert( const medialibrary::IPlaylist* input, vlc_ml_playlist_t& output )
bool Convert( const medialibrary::IFolder* input, vlc_ml_folder_t& output )
{
output.i_id = input->id();
+
+ output.i_nb_media = input->nbMedia();
+
output.b_banned = input->isBanned();
+
+ if ( strdup_helper( input->name(), output.psz_name ) == false )
+ return false;
+
try
{
- if ( strdup_helper( input->mrl(), output.psz_mrl ) == false )
+ if (strdup_helper(input->mrl(), output.psz_mrl) == false)
return false;
+
output.b_present = true;
}
catch ( const medialibrary::fs::errors::DeviceRemoved& )
{
output.psz_mrl = nullptr;
+
output.b_present = false;
}
+
return true;
}
=====================================
modules/misc/medialibrary/medialibrary.cpp
=====================================
@@ -740,10 +740,39 @@ int MediaLibrary::List( int listQuery, const vlc_ml_query_params_t* params, va_l
psz_pattern = params->psz_pattern;
paramsPtr = &p;
}
+
+ medialibrary::IMedia::Type type = medialibrary::IMedia::Type::Unknown;
+
+ switch ( listQuery )
+ {
+ case VLC_ML_LIST_MEDIA_OF:
+ case VLC_ML_COUNT_MEDIA_OF:
+ // N/A default value
+ break;
+ case VLC_ML_LIST_VIDEO_OF:
+ case VLC_ML_COUNT_VIDEO_OF:
+ type = medialibrary::IMedia::Type::Video;
+ break;
+ case VLC_ML_LIST_AUDIO_OF:
+ case VLC_ML_COUNT_AUDIO_OF:
+ type = medialibrary::IMedia::Type::Audio;
+ break;
+ case VLC_ML_LIST_FOLDERS_BY_TYPE:
+ case VLC_ML_COUNT_FOLDERS_BY_TYPE:
+ type = static_cast<medialibrary::IMedia::Type>(va_arg(args, int));
+ break;
+ default:
+ break;
+ }
+
switch ( listQuery )
{
case VLC_ML_LIST_MEDIA_OF:
case VLC_ML_COUNT_MEDIA_OF:
+ case VLC_ML_LIST_VIDEO_OF:
+ case VLC_ML_COUNT_VIDEO_OF:
+ case VLC_ML_LIST_AUDIO_OF:
+ case VLC_ML_COUNT_AUDIO_OF:
case VLC_ML_LIST_ARTISTS_OF:
case VLC_ML_COUNT_ARTISTS_OF:
case VLC_ML_LIST_ALBUMS_OF:
@@ -755,6 +784,7 @@ int MediaLibrary::List( int listQuery, const vlc_ml_query_params_t* params, va_l
default:
break;
}
+
switch( listQuery )
{
case VLC_ML_LIST_ALBUM_TRACKS:
@@ -971,7 +1001,14 @@ int MediaLibrary::List( int listQuery, const vlc_ml_query_params_t* params, va_l
case VLC_ML_COUNT_GROUPS:
case VLC_ML_LIST_GROUP_MEDIA:
case VLC_ML_COUNT_GROUP_MEDIA:
- return listGroup( listQuery, paramsPtr, psz_pattern, nbItems, offset, args );
+ return listGroup( listQuery, paramsPtr, type, psz_pattern, nbItems, offset, args );
+ case VLC_ML_LIST_FOLDERS:
+ case VLC_ML_COUNT_FOLDERS:
+ case VLC_ML_LIST_FOLDERS_BY_TYPE:
+ case VLC_ML_COUNT_FOLDERS_BY_TYPE:
+ case VLC_ML_LIST_FOLDER_MEDIA:
+ case VLC_ML_COUNT_FOLDER_MEDIA:
+ return listFolder( listQuery, paramsPtr, type, psz_pattern, nbItems, offset, args );
case VLC_ML_LIST_PLAYLIST_MEDIA:
case VLC_ML_COUNT_PLAYLIST_MEDIA:
case VLC_ML_LIST_PLAYLISTS:
@@ -1067,42 +1104,6 @@ int MediaLibrary::List( int listQuery, const vlc_ml_query_params_t* params, va_l
*( va_arg( args, size_t* ) ) = query == nullptr ? 0 : query->count();
break;
}
- case VLC_ML_LIST_FOLDERS:
- {
- const auto query = m_ml->folders( medialibrary::IMedia::Type::Unknown, paramsPtr );
- if ( query == nullptr )
- return VLC_EGENERIC;
- auto* res = ml_convert_list<vlc_ml_folder_list_t, vlc_ml_folder_t>( query->all() );
- *( va_arg( args, vlc_ml_folder_list_t** ) ) = res;
- break;
- }
- case VLC_ML_COUNT_FOLDERS:
- {
- const auto query = m_ml->folders( medialibrary::IMedia::Type::Unknown, paramsPtr );
- *( va_arg( args, size_t* ) ) = query == nullptr ? 0 : query->count();
- break;
- }
- case VLC_ML_LIST_FOLDER_MEDIAS:
- {
- const auto folder = m_ml->folder( va_arg( args, int64_t ) );
- if ( folder == nullptr )
- return VLC_EGENERIC;
- const auto query = folder->media( medialibrary::IMedia::Type::Unknown, paramsPtr );
- if ( query == nullptr )
- return VLC_EGENERIC;
- auto* res = ml_convert_list<vlc_ml_media_list_t, vlc_ml_media_t>( query->all() );
- *( va_arg( args, vlc_ml_media_list_t** ) ) = res;
- break;
- }
- case VLC_ML_COUNT_FOLDER_MEDIAS:
- {
- const auto folder = m_ml->folder( va_arg( args, int64_t ) );
- if ( folder == nullptr )
- return VLC_EGENERIC;
- const auto query = folder->media( medialibrary::IMedia::Type::Unknown, paramsPtr );
- *( va_arg( args, size_t* ) ) = query == nullptr ? 0 : query->count();
- break;
- }
}
return VLC_SUCCESS;
}
@@ -1506,6 +1507,8 @@ int MediaLibrary::filterListChildrenQuery( int query, int parentType )
switch( query )
{
case VLC_ML_LIST_MEDIA_OF:
+ case VLC_ML_LIST_VIDEO_OF:
+ case VLC_ML_LIST_AUDIO_OF:
switch ( parentType )
{
case VLC_ML_PARENT_ALBUM:
@@ -1518,12 +1521,16 @@ int MediaLibrary::filterListChildrenQuery( int query, int parentType )
return VLC_ML_LIST_GENRE_TRACKS;
case VLC_ML_PARENT_GROUP:
return VLC_ML_LIST_GROUP_MEDIA;
+ case VLC_ML_PARENT_FOLDER:
+ return VLC_ML_LIST_FOLDER_MEDIA;
case VLC_ML_PARENT_PLAYLIST:
return VLC_ML_LIST_PLAYLIST_MEDIA;
default:
vlc_assert_unreachable();
}
case VLC_ML_COUNT_MEDIA_OF:
+ case VLC_ML_COUNT_VIDEO_OF:
+ case VLC_ML_COUNT_AUDIO_OF:
switch ( parentType )
{
case VLC_ML_PARENT_ALBUM:
@@ -1536,6 +1543,8 @@ int MediaLibrary::filterListChildrenQuery( int query, int parentType )
return VLC_ML_COUNT_GENRE_TRACKS;
case VLC_ML_PARENT_GROUP:
return VLC_ML_COUNT_GROUP_MEDIA;
+ case VLC_ML_PARENT_FOLDER:
+ return VLC_ML_COUNT_FOLDER_MEDIA;
case VLC_ML_PARENT_PLAYLIST:
return VLC_ML_COUNT_PLAYLIST_MEDIA;
default:
@@ -1792,7 +1801,8 @@ int MediaLibrary::listGenre( int listQuery, const medialibrary::QueryParameters*
}
int MediaLibrary::listGroup( int listQuery, const medialibrary::QueryParameters* paramsPtr,
- const char* pattern, uint32_t nbItems, uint32_t offset, va_list args )
+ medialibrary::IMedia::Type type, const char* pattern,
+ uint32_t nbItems, uint32_t offset, va_list args )
{
switch( listQuery )
{
@@ -1804,7 +1814,7 @@ int MediaLibrary::listGroup( int listQuery, const medialibrary::QueryParameters*
if ( pattern )
query = m_ml->searchMediaGroups( pattern, paramsPtr );
else
- query = m_ml->mediaGroups( medialibrary::IMedia::Type::Unknown, paramsPtr );
+ query = m_ml->mediaGroups( type, paramsPtr );
if ( query == nullptr )
return VLC_EGENERIC;
@@ -1837,10 +1847,9 @@ int MediaLibrary::listGroup( int listQuery, const medialibrary::QueryParameters*
medialibrary::Query<medialibrary::IMedia> query;
if ( pattern )
- query = group->searchMedia( pattern, medialibrary::IMedia::Type::Unknown,
- paramsPtr );
+ query = group->searchMedia( pattern, type, paramsPtr );
else
- query = group->media( medialibrary::IMedia::Type::Unknown, paramsPtr );
+ query = group->media( type, paramsPtr );
if ( query == nullptr )
return VLC_EGENERIC;
@@ -1867,6 +1876,86 @@ int MediaLibrary::listGroup( int listQuery, const medialibrary::QueryParameters*
}
}
+int MediaLibrary::listFolder(int listQuery, const medialibrary::QueryParameters * paramsPtr,
+ medialibrary::IMedia::Type type, const char * pattern,
+ uint32_t nbItems, uint32_t offset, va_list args)
+{
+ switch (listQuery)
+ {
+ case VLC_ML_LIST_FOLDERS:
+ case VLC_ML_COUNT_FOLDERS:
+ case VLC_ML_LIST_FOLDERS_BY_TYPE:
+ case VLC_ML_COUNT_FOLDERS_BY_TYPE:
+ {
+ medialibrary::Query<medialibrary::IFolder> query;
+
+ if (pattern)
+ query = m_ml->searchFolders(pattern, type, paramsPtr);
+ else
+ query = m_ml->folders(type, paramsPtr);
+
+ if (query == nullptr)
+ return VLC_EGENERIC;
+
+ switch (listQuery)
+ {
+ case VLC_ML_LIST_FOLDERS:
+ case VLC_ML_LIST_FOLDERS_BY_TYPE:
+ *va_arg(args, vlc_ml_folder_list_t **) =
+ ml_convert_list<vlc_ml_folder_list_t, vlc_ml_folder_t>
+ (query->items(nbItems, offset));
+ return VLC_SUCCESS;
+
+ case VLC_ML_COUNT_FOLDERS:
+ case VLC_ML_COUNT_FOLDERS_BY_TYPE:
+ *va_arg(args, size_t *) = query->count();
+ return VLC_SUCCESS;
+
+ default:
+ vlc_assert_unreachable();
+ }
+ }
+
+ case VLC_ML_LIST_FOLDER_MEDIA:
+ case VLC_ML_COUNT_FOLDER_MEDIA:
+ {
+ medialibrary::FolderPtr folder = m_ml->folder(va_arg(args, int64_t));
+
+ if (folder == nullptr)
+ return VLC_EGENERIC;
+
+ medialibrary::Query<medialibrary::IMedia> query;
+
+ if (pattern)
+ query = folder->searchMedia(pattern, type, paramsPtr);
+ else
+ query = folder->media(type, paramsPtr);
+
+ if (query == nullptr)
+ return VLC_EGENERIC;
+
+ switch (listQuery)
+ {
+ case VLC_ML_LIST_FOLDER_MEDIA:
+ *va_arg(args, vlc_ml_media_list_t **) =
+ ml_convert_list<vlc_ml_media_list_t, vlc_ml_media_t>
+ (query->items(nbItems, offset));
+ return VLC_SUCCESS;
+
+ case VLC_ML_COUNT_FOLDER_MEDIA:
+ *va_arg(args, size_t *) = query->count();
+ return VLC_SUCCESS;
+
+ default:
+ vlc_assert_unreachable();
+ }
+ }
+
+ default:
+ vlc_assert_unreachable();
+ }
+}
+
int MediaLibrary::listPlaylist( int listQuery, const medialibrary::QueryParameters* paramsPtr,
const char* pattern, uint32_t nbItems, uint32_t offset, va_list args )
{
=====================================
modules/misc/medialibrary/medialibrary.h
=====================================
@@ -170,7 +170,11 @@ private:
int listGenre( int listQuery, const medialibrary::QueryParameters* paramsPtr,
const char* pattern, uint32_t nbItems, uint32_t offset, va_list args );
int listGroup( int listQuery, const medialibrary::QueryParameters* paramsPtr,
- const char* pattern, uint32_t nbItems, uint32_t offset, va_list args );
+ medialibrary::IMedia::Type type, const char* pattern, uint32_t nbItems,
+ uint32_t offset, va_list args );
+ int listFolder( int listQuery, const medialibrary::QueryParameters* paramsPtr,
+ medialibrary::IMedia::Type type, const char* pattern, uint32_t nbItems,
+ uint32_t offset, va_list args );
int listPlaylist( int listQuery, const medialibrary::QueryParameters* paramsPtr,
const char* pattern, uint32_t nbItems, uint32_t offset, va_list args );
int listMedia( int listQuery, const medialibrary::QueryParameters* paramsPtr,
=====================================
po/POTFILES.in
=====================================
@@ -770,12 +770,12 @@ modules/gui/qt/dialogs/plugins/addons_manager.cpp
modules/gui/qt/dialogs/plugins/addons_manager.hpp
modules/gui/qt/medialibrary/mlbookmarkmodel.cpp
modules/gui/qt/medialibrary/mlbookmarkmodel.hpp
+modules/gui/qt/medialibrary/mlfolder.cpp
+modules/gui/qt/medialibrary/mlfolder.hpp
modules/gui/qt/medialibrary/mlfoldersmodel.cpp
modules/gui/qt/medialibrary/mlfoldersmodel.hpp
modules/gui/qt/medialibrary/mlgroup.cpp
modules/gui/qt/medialibrary/mlgroup.hpp
-modules/gui/qt/medialibrary/mlgrouplistmodel.cpp
-modules/gui/qt/medialibrary/mlgrouplistmodel.hpp
modules/gui/qt/medialibrary/mlitemcover.cpp
modules/gui/qt/medialibrary/mlitemcover.hpp
modules/gui/qt/medialibrary/mlplaylistlistmodel.cpp
@@ -784,6 +784,10 @@ modules/gui/qt/medialibrary/mlplaylistmedia.cpp
modules/gui/qt/medialibrary/mlplaylistmedia.hpp
modules/gui/qt/medialibrary/mlplaylistmodel.cpp
modules/gui/qt/medialibrary/mlplaylistmodel.hpp
+modules/gui/qt/medialibrary/mlvideofoldersmodel.cpp
+modules/gui/qt/medialibrary/mlvideofoldersmodel.hpp
+modules/gui/qt/medialibrary/mlvideogroupsmodel.cpp
+modules/gui/qt/medialibrary/mlvideogroupsmodel.hpp
modules/gui/qt/menus/menus.cpp
modules/gui/qt/menus/menus.hpp
modules/gui/qt/qt.cpp
View it on GitLab: https://code.videolan.org/videolan/vlc/-/compare/21931db0aa9b2771851bc5bb397b99b839be2ba2...6fb0c5f38a18b9417c759fd36762b4de9fae5194
--
View it on GitLab: https://code.videolan.org/videolan/vlc/-/compare/21931db0aa9b2771851bc5bb397b99b839be2ba2...6fb0c5f38a18b9417c759fd36762b4de9fae5194
You're receiving this email because of your account on code.videolan.org.
VideoLAN code repository instance
More information about the vlc-commits
mailing list