Create new playlists on the stack
- Only works for new sets - Set a callback function when created - Add a right-click menu to the ocarina treeview - Remove songs from playlist when picking next song Signed-off-by: Bryan Schumaker <bjschuma@gmail.com>
This commit is contained in:
parent
78787d9cf5
commit
15aabfcff0
|
@ -12,6 +12,11 @@ enum PlaylistFlags {
|
|||
PL_STATIC = (1 << 1),
|
||||
};
|
||||
|
||||
enum PlaylistType {
|
||||
PLIST_SET,
|
||||
PLIST_QUEUE,
|
||||
};
|
||||
|
||||
#define RENDER(x) \
|
||||
if (renderer) { \
|
||||
renderer->x; \
|
||||
|
@ -28,7 +33,9 @@ namespace libsaria
|
|||
private:
|
||||
unsigned int flags;
|
||||
list<Track *>::iterator cur;
|
||||
|
||||
void incr_iter();
|
||||
Track *picked_next();
|
||||
|
||||
protected:
|
||||
string name;
|
||||
|
|
|
@ -21,6 +21,8 @@ namespace libsaria
|
|||
virtual void insert_prepare();
|
||||
virtual void insert(Track *, unsigned int);
|
||||
virtual void insert_done();
|
||||
|
||||
virtual void remove_index(unsigned int);
|
||||
};
|
||||
|
||||
}; /* Namespace: libsaria */
|
||||
|
|
|
@ -18,7 +18,9 @@ namespace libsaria
|
|||
};
|
||||
|
||||
Playlist *new_playlist(string, unsigned int);
|
||||
//void add_to_playlist(list<sid_t> &);
|
||||
void set_on_new_playlist(void (*)(Playlist *));
|
||||
void create_new_playlist(list<Track *> &, PlaylistType);
|
||||
|
||||
Playlist *stack_top();
|
||||
void stack_top_pop();
|
||||
void stack_init();
|
||||
|
|
|
@ -14,20 +14,26 @@ namespace ocarina
|
|||
GtkWidget *box;
|
||||
GtkWidget *treeview;
|
||||
GtkListStore *liststore;
|
||||
GtkTreeSelection *treesel;
|
||||
|
||||
void set_label_text();
|
||||
void setup_treeview();
|
||||
|
||||
public:
|
||||
Playlist(unsigned int);
|
||||
Playlist(libsaria::Playlist *);
|
||||
~Playlist();
|
||||
|
||||
void right_click(guint, guint64);
|
||||
void list_selected_tracks(list<libsaria::Track *> &);
|
||||
|
||||
void set_playlist(libsaria::Playlist *);
|
||||
|
||||
void insert_prepare();
|
||||
void insert(libsaria::Track *, unsigned int);
|
||||
void insert_done();
|
||||
|
||||
void remove_index(unsigned int);
|
||||
};
|
||||
|
||||
namespace playlist
|
||||
|
|
|
@ -16,8 +16,9 @@ namespace libsaria
|
|||
void Playlist::add_sorted(list<Track *> &tracks)
|
||||
{
|
||||
list<Track *> copy;
|
||||
list<Track *>::iterator it, cur;
|
||||
list<Track *>::iterator it, cur_it;
|
||||
unsigned int ins_index;
|
||||
bool update_cur = (plist.size() == 0);
|
||||
|
||||
RENDER(insert_prepare());
|
||||
tracks.sort(compare_tracks);
|
||||
|
@ -27,8 +28,8 @@ namespace libsaria
|
|||
|
||||
ins_index = 0;
|
||||
it = tracks.begin();
|
||||
for (cur = plist.begin(); cur != plist.end(); cur++) {
|
||||
if ((*cur) == (*it)) {
|
||||
for (cur_it = plist.begin(); cur_it != plist.end(); cur_it++) {
|
||||
if ((*cur_it) == (*it)) {
|
||||
RENDER( insert(*it, ins_index) );
|
||||
if (it++ == tracks.end())
|
||||
break;
|
||||
|
@ -36,6 +37,9 @@ namespace libsaria
|
|||
ins_index++;
|
||||
}
|
||||
|
||||
if (update_cur)
|
||||
cur = plist.begin();
|
||||
|
||||
RENDER(insert_done());
|
||||
}
|
||||
|
||||
|
|
|
@ -1,8 +1,9 @@
|
|||
// Copyright (c) 2012 Bryan Schumaker.
|
||||
#include <libsaria/playlist.h>
|
||||
//#include <libsaria/renderer.h>
|
||||
#include <libsaria/renderer.h>
|
||||
#include <libsaria/index.h>
|
||||
#include <libsaria/prefs.h>
|
||||
#include <libsaria/print.h>
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
|
@ -24,6 +25,26 @@ namespace libsaria
|
|||
if (cur == plist.end())
|
||||
cur = plist.begin();
|
||||
}
|
||||
|
||||
Track *Playlist::picked_next()
|
||||
{
|
||||
Track *res = (*cur);
|
||||
unsigned int index = 0;
|
||||
list<Track *>::iterator it;
|
||||
|
||||
if (flags & PL_NO_DRAIN)
|
||||
return res;
|
||||
|
||||
for (it = plist.begin(); it != cur; it++)
|
||||
index++;
|
||||
|
||||
cur = plist.erase(cur);
|
||||
if (cur == plist.end())
|
||||
cur = plist.begin();
|
||||
|
||||
RENDER(remove_index(index));
|
||||
return res;
|
||||
}
|
||||
/*
|
||||
bool Playlist::pick_next(list<Track *>::iterator &it)
|
||||
{
|
||||
|
@ -81,11 +102,16 @@ namespace libsaria
|
|||
if (size == 0)
|
||||
return NULL;
|
||||
|
||||
if (size == 1) {
|
||||
cur = plist.begin();
|
||||
return picked_next();
|
||||
}
|
||||
|
||||
n = rand() % ((size * 3) / 4);
|
||||
for (unsigned int i = 0; i < n; i++)
|
||||
incr_iter();
|
||||
|
||||
return (*cur);
|
||||
return picked_next();
|
||||
}
|
||||
|
||||
/*Track *Playlist::next()
|
||||
|
|
|
@ -32,6 +32,10 @@ namespace libsaria
|
|||
{
|
||||
}
|
||||
|
||||
void PlaylistRenderer::remove_index(unsigned int index)
|
||||
{
|
||||
}
|
||||
|
||||
/*void PlaylistRenderer::set_playlist(Playlist *plist, bool del_render)
|
||||
{
|
||||
playlist = plist;
|
||||
|
|
|
@ -7,6 +7,9 @@
|
|||
#include <sstream>
|
||||
using namespace std;
|
||||
|
||||
static unsigned int next_playlist = 0;
|
||||
static void (*on_new_playlist)(libsaria::Playlist *) = NULL;
|
||||
|
||||
static list<libsaria::Playlist *> playlist_stack;
|
||||
|
||||
/*static void plist_loaded()
|
||||
|
@ -14,6 +17,13 @@ static list<libsaria::Playlist *> playlist_stack;
|
|||
trigger_callback(NEW_PLAYLIST);
|
||||
}*/
|
||||
|
||||
static string get_next_name()
|
||||
{
|
||||
stringstream s;
|
||||
s << next_playlist;
|
||||
return s.str();
|
||||
}
|
||||
|
||||
namespace libsaria
|
||||
{
|
||||
|
||||
|
@ -30,12 +40,29 @@ namespace libsaria
|
|||
track->play_now();
|
||||
}
|
||||
|
||||
Playlist *new_playlist(string file, unsigned int flags)
|
||||
void set_on_new_playlist(void (*func)(Playlist *))
|
||||
{
|
||||
/*Playlist *plist = new Playlist(file, flags);
|
||||
stack_playlist(plist);
|
||||
return plist;*/
|
||||
return NULL;
|
||||
on_new_playlist = func;
|
||||
}
|
||||
|
||||
void create_new_playlist(list<Track *> &tracks, PlaylistType type)
|
||||
{
|
||||
Playlist *plist;
|
||||
|
||||
switch (type) {
|
||||
case PLIST_SET:
|
||||
plist = new Set("Set_" + get_next_name(), PL_NONE);
|
||||
break;
|
||||
case PLIST_QUEUE:
|
||||
return;
|
||||
};
|
||||
|
||||
if (on_new_playlist)
|
||||
on_new_playlist(plist);
|
||||
plist->add_tracks(tracks);
|
||||
|
||||
stack::push(plist);
|
||||
next_playlist++;
|
||||
}
|
||||
|
||||
/*void add_to_playlist(list<sid_t> &ids)
|
||||
|
|
|
@ -1,14 +1,21 @@
|
|||
// Copyright (c) 2011 Bryan Schumaker
|
||||
#include <ocarina/playlist.h>
|
||||
#include <libsaria/library.h>
|
||||
#include <libsaria/stack.h>
|
||||
|
||||
static ocarina::Playlist library_renderer(PL_STATIC);
|
||||
|
||||
namespace ocarina
|
||||
{
|
||||
|
||||
void on_new_playlist(libsaria::Playlist *plist)
|
||||
{
|
||||
new Playlist(plist);
|
||||
}
|
||||
|
||||
void playlist::init()
|
||||
{
|
||||
libsaria::set_on_new_playlist(on_new_playlist);
|
||||
library_renderer.set_playlist(libsaria::library::get_playlist());
|
||||
}
|
||||
|
||||
|
|
|
@ -38,4 +38,12 @@ namespace ocarina
|
|||
set_label_text();
|
||||
}
|
||||
|
||||
void Playlist::remove_index(unsigned int index)
|
||||
{
|
||||
GtkTreeIter iter;
|
||||
gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(liststore), &iter, NULL, index);
|
||||
gtk_list_store_remove(liststore, &iter);
|
||||
set_label_text();
|
||||
}
|
||||
|
||||
};
|
||||
|
|
|
@ -0,0 +1,63 @@
|
|||
// Copyright (c) 2012 Bryan Schumaker
|
||||
#include <ocarina/playlist.h>
|
||||
#include "playlist.h"
|
||||
|
||||
#include <libsaria/stack.h>
|
||||
#include <libsaria/track.h>
|
||||
|
||||
#include <list>
|
||||
using namespace std;
|
||||
|
||||
#define BUTTON_RIGHT 3
|
||||
|
||||
static void new_playlist(ocarina::Playlist *plist, PlaylistType type)
|
||||
{
|
||||
list<libsaria::Track *> tracks;
|
||||
plist->list_selected_tracks(tracks);
|
||||
libsaria::create_new_playlist(tracks, type);
|
||||
}
|
||||
|
||||
static void new_queue(GtkMenuItem *menu, gpointer data)
|
||||
{
|
||||
new_playlist((ocarina::Playlist *)data, PLIST_QUEUE);
|
||||
}
|
||||
|
||||
static void new_set(GtkMenuItem *menu, gpointer data)
|
||||
{
|
||||
new_playlist((ocarina::Playlist *)data, PLIST_SET);
|
||||
}
|
||||
|
||||
static GtkWidget *menu_item(const char *text, void (*func)(GtkMenuItem *, gpointer),
|
||||
ocarina::Playlist *plist)
|
||||
{
|
||||
GtkWidget *widget = gtk_menu_item_new_with_label(text);
|
||||
g_signal_connect(widget, "activate", G_CALLBACK(func), plist);
|
||||
return widget;
|
||||
}
|
||||
|
||||
void show_rc_menu(GtkWidget *widget, GdkEvent *event, gpointer data)
|
||||
{
|
||||
ocarina::Playlist *plist = (ocarina::Playlist *)data;
|
||||
|
||||
if (event->button.button != BUTTON_RIGHT)
|
||||
return;
|
||||
plist->right_click(event->button.button, event->button.time);
|
||||
}
|
||||
|
||||
namespace ocarina
|
||||
{
|
||||
|
||||
void Playlist::right_click(guint button, guint64 time)
|
||||
{
|
||||
GtkWidget *menu = gtk_menu_new();
|
||||
GtkWidget *queue = menu_item("Add to new queue", new_queue, this);
|
||||
GtkWidget *set = menu_item("Add to new set", new_set, this);
|
||||
|
||||
gtk_menu_append(GTK_MENU(menu), queue);
|
||||
gtk_menu_append(GTK_MENU(menu), set);
|
||||
|
||||
gtk_widget_show_all(menu);
|
||||
gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, button, time);
|
||||
}
|
||||
|
||||
}
|
|
@ -2,9 +2,21 @@
|
|||
#include <ocarina/playlist.h>
|
||||
#include <ocarina/body.h>
|
||||
|
||||
#include <libsaria/track.h>
|
||||
|
||||
#include <sstream>
|
||||
using namespace std;
|
||||
|
||||
static void selected_foreach_list(GtkTreeModel *model, GtkTreePath *path,
|
||||
GtkTreeIter *iter, gpointer data)
|
||||
{
|
||||
libsaria::Track *track;
|
||||
list<libsaria::Track *> *tracks = (list<libsaria::Track *> *)data;
|
||||
|
||||
gtk_tree_model_get(model, iter, 0, &track, -1);
|
||||
tracks->push_back(track);
|
||||
}
|
||||
|
||||
namespace ocarina
|
||||
{
|
||||
|
||||
|
@ -12,6 +24,11 @@ namespace ocarina
|
|||
{
|
||||
}
|
||||
|
||||
Playlist::Playlist(libsaria::Playlist *plist): libsaria::PlaylistRenderer(PL_NONE)
|
||||
{
|
||||
set_playlist(plist);
|
||||
}
|
||||
|
||||
Playlist::~Playlist()
|
||||
{
|
||||
}
|
||||
|
@ -28,6 +45,11 @@ namespace ocarina
|
|||
gtk_label_set_text(GTK_LABEL(label), text.c_str());
|
||||
}
|
||||
|
||||
void Playlist::list_selected_tracks(list<libsaria::Track *> &tracks)
|
||||
{
|
||||
gtk_tree_selection_selected_foreach(treesel, selected_foreach_list, &tracks);
|
||||
}
|
||||
|
||||
void Playlist::set_playlist(libsaria::Playlist *p)
|
||||
{
|
||||
libsaria::PlaylistRenderer::set_playlist(p);
|
||||
|
|
|
@ -0,0 +1,2 @@
|
|||
// Copyright (c) 2012 Bryan Schumaker
|
||||
void show_rc_menu(GtkWidget *widget, GdkEvent *event, gpointer data);
|
|
@ -1,5 +1,7 @@
|
|||
// Copyright (c) 2012 Bryan Schumaker
|
||||
#include <ocarina/playlist.h>
|
||||
#include "playlist.h"
|
||||
|
||||
#include <libsaria/track.h>
|
||||
|
||||
struct column_info {
|
||||
|
@ -86,7 +88,11 @@ namespace ocarina
|
|||
treeview = gtk_tree_view_new();
|
||||
liststore = setup_liststore(treeview);
|
||||
|
||||
treesel = gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview));
|
||||
gtk_tree_selection_set_mode(treesel, GTK_SELECTION_MULTIPLE);
|
||||
|
||||
g_signal_connect(treeview, "row-activated", G_CALLBACK(track_selected), NULL);
|
||||
g_signal_connect(treeview, "button-release-event", G_CALLBACK(show_rc_menu), this);
|
||||
|
||||
gtk_tree_view_set_rules_hint(GTK_TREE_VIEW(treeview), TRUE);
|
||||
gtk_tree_view_set_model(GTK_TREE_VIEW(treeview), GTK_TREE_MODEL(liststore));
|
||||
|
|
Loading…
Reference in New Issue