ocarina/gui/wires.cpp

300 lines
6.9 KiB
C++

/*
* Copyright 2014 (c) Anna Schumaker.
*/
#include <audio.h>
#include <callback.h>
#include <idle.h>
#include <library.h>
#include <ocarina.h>
#include <print.h>
static bool audio_playing = false;
static Glib::RefPtr<Gtk::Builder> builder;
void enable_idle();
void enable_timeout();
template <class T>
void get_object(const std::string &, Glib::RefPtr<T> &);
/*
* Control functions
*/
static void on_play()
{
get_button("o_play")->hide();
get_button("o_pause")->show();
audio_playing = true;
enable_timeout();
}
static void on_pause()
{
get_button("o_play")->show();
get_button("o_pause")->hide();
audio_playing = false;
}
static void on_track_loaded(library :: Song &song)
{
Gtk::Label *title, *artist, *album, *duration;
builder->get_widget("o_title", title);
builder->get_widget("o_artist", artist);
builder->get_widget("o_album", album);
builder->get_widget("o_total_time", duration);
title->set_markup("<span size='xx-large'>" + song.track->title + "</span>");
artist->set_markup("<span size='x-large'>By: " + song.artist->primary_key + "</span>");
album->set_markup("<span size='x-large'>From: " + song.album->name + "</span>");
duration->set_text(song.track->length_str);
}
/*
* Collection manager functions
*/
static class CollectionColumns : public Gtk::TreeModelColumnRecord {
public:
CollectionColumns()
{ add(c_col_id); add(c_col_enabled); add(c_col_size); add(c_col_path); }
Gtk::TreeModelColumn<unsigned int> c_col_id;
Gtk::TreeModelColumn<bool> c_col_enabled;
Gtk::TreeModelColumn<unsigned int> c_col_size;
Gtk::TreeModelColumn<Glib::ustring> c_col_path;
} collection_cols;
static void on_collection_ok()
{
std::string path;
Gtk::FileChooserWidget *chooser;
get_builder()->get_widget("o_collection_chooser", chooser);
path = chooser->get_filename();
library::add_path(path);
enable_idle();
}
static void on_collection_update()
{
library :: update_all();
enable_idle();
}
static void on_collection_import()
{
library :: import();
enable_idle();
}
static void on_collection_row_activated(const Gtk::TreePath &path,
Gtk::TreeViewColumn *col)
{
Gtk::FileChooser *chooser;
Glib::RefPtr<Gtk::ListStore> list;
get_object("o_collection_dirs", list);
builder->get_widget("o_collection_chooser", chooser);
Gtk::TreeModel::Row row = *(list->get_iter(path));
Glib::ustring dir = row[collection_cols.c_col_path];
chooser->set_current_folder(dir);
}
#ifndef CONFIG_TEST
static
#endif /* CONFIG_TEST */
void do_collection_delete()
{
Gtk::TreePath path;
Gtk::TreeViewColumn *col;
Gtk::TreeView *treeview;
builder->get_widget("o_collection_treeview", treeview);
treeview->get_cursor(path, col);
if (path) {
Glib::RefPtr<Gtk::ListStore> list;
get_object("o_collection_dirs", list);
Gtk::TreeModel::Row row = *(list->get_iter(path));
library :: del_path(row[collection_cols.c_col_id]);
list->erase(row);
}
}
static bool on_collection_key_pressed(GdkEventKey *event)
{
std::string key = gdk_keyval_name(event->keyval);
if (key == "Delete") {
do_collection_delete();
return true;
}
return false;
}
#ifndef CONFIG_TEST
static
#endif /* CONFIG_TEST */
void on_collection_toggled(const Glib::ustring &path)
{
Glib::RefPtr<Gtk::ListStore> list;
get_object("o_collection_dirs", list);
Gtk::TreeModel::Row row = *(list->get_iter(path));
row[collection_cols.c_col_enabled] = !row[collection_cols.c_col_enabled];
library :: set_enabled(row[collection_cols.c_col_id],
row[collection_cols.c_col_enabled]);
}
static void on_library_add(unsigned int id, library :: Library *path)
{
Gtk::TreeModel::Row row;
Glib::RefPtr<Gtk::ListStore> list;
get_object("o_collection_dirs", list);
row = *(list->append());
row[collection_cols.c_col_id] = id;
row[collection_cols.c_col_enabled] = path->enabled;
row[collection_cols.c_col_size] = path->size;
row[collection_cols.c_col_path] = path->root_path;
}
static void on_library_update(unsigned int id, library :: Library *path)
{
Gtk::TreeModel::Row row;
Glib::RefPtr<Gtk::ListStore> list;
get_object("o_collection_dirs", list);
Gtk::TreeModel::Children children = list->children();
for (Gtk::TreeModel::Children::iterator it = children.begin();
it != children.end(); it++) {
row = *it;
if (row[collection_cols.c_col_id] == id)
row[collection_cols.c_col_size] = path->size;
}
}
/*
* Idle func
*/
bool on_idle()
{
Gtk::ProgressBar *prog;
bool ret = idle::run_task();
builder->get_widget("o_idle_progress", prog);
if (ret == false)
prog->hide();
else {
prog->show();
prog->set_fraction(idle::get_progress());
}
return ret;
}
void enable_idle()
{
Glib::signal_idle().connect(sigc::ptr_fun(on_idle));
}
/*
* Timeout function
*/
bool on_timeout()
{
Gtk::Label *position;
Glib::RefPtr<Gtk::Adjustment> bar;
builder->get_widget("o_cur_position", position);
get_object("o_progress", bar);
position->set_text(audio :: position_str());
bar->set_upper(audio :: duration());
bar->set_value(audio :: position());
return audio_playing;
}
void enable_timeout()
{
Glib::signal_timeout().connect(sigc::ptr_fun(on_timeout), 500);
}
/*
* Ocarina functions
*/
Glib::RefPtr<Gtk::Builder> &get_builder()
{
return builder;
}
Gtk::Button *get_button(const std::string &name)
{
Gtk::Button *button;
builder->get_widget(name, button);
return button;
}
template <class T>
static void get_object(const std::string &name, Glib::RefPtr<T> &obj)
{
obj = Glib::RefPtr<T>::cast_static(builder->get_object(name));
}
static void connect_button(const std::string &name, void (*func)())
{
get_button(name)->signal_clicked().connect(sigc::ptr_fun(func));
}
Gtk::Window *connect_wires()
{
Gtk::Window *window;
struct Callbacks *cb = get_callbacks();
Glib::RefPtr<Gtk::ListStore> list;
Glib::RefPtr<Gtk::CellRendererToggle> toggle;
Gtk::TreeView *treeview;
builder = Gtk::Builder::create();
builder->add_from_file("gui/ocarina6.glade");
builder->get_widget("o_window", window);
/* Controls */
cb->on_play = on_play;
cb->on_pause = on_pause;
cb->on_track_loaded = on_track_loaded;
connect_button("o_play", audio::play);
connect_button("o_pause", audio::pause);
connect_button("o_stop", audio::stop);
connect_button("o_prev", audio::previous);
connect_button("o_next", audio::next);
/* Collection manager */
cb->on_library_add = on_library_add;
cb->on_library_update = on_library_update;
get_object("o_collection_dirs", list);
list->set_sort_column(collection_cols.c_col_path, Gtk::SORT_ASCENDING);
builder->get_widget("o_collection_treeview", treeview);
get_object("o_collection_toggle", toggle);
treeview->signal_row_activated().connect(sigc::ptr_fun(on_collection_row_activated));
treeview->signal_key_press_event().connect(sigc::ptr_fun(on_collection_key_pressed));
toggle->signal_toggled().connect(sigc::ptr_fun(on_collection_toggled));
connect_button("o_collection_ok", on_collection_ok);
connect_button("o_collection_update", on_collection_update);
connect_button("o_collection_import", on_collection_import);
/* Set up other tabs */
init_tabs();
return window;
}