Give route groups their own colour, settable from the route
group dialogue. Americanise spelling of color in a few places to avoid confusion. Fixes #4224. Addresses parts of #2650 and #4064. git-svn-id: svn://localhost/ardour2/branches/3.0@10030 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
parent
9b7ae4cccc
commit
7d32cf3813
|
@ -38,6 +38,7 @@
|
|||
#include "ardour_ui.h"
|
||||
#include "gui_object.h"
|
||||
#include "axis_view.h"
|
||||
#include "utils.h"
|
||||
#include "i18n.h"
|
||||
|
||||
using namespace std;
|
||||
|
@ -60,41 +61,7 @@ AxisView::~AxisView()
|
|||
Gdk::Color
|
||||
AxisView::unique_random_color()
|
||||
{
|
||||
Gdk::Color newcolor;
|
||||
|
||||
while (1) {
|
||||
|
||||
/* avoid neon/glowing tones by limiting them to the
|
||||
"inner section" (paler) of a color wheel/circle.
|
||||
*/
|
||||
|
||||
const int32_t max_saturation = 48000; // 65535 would open up the whole color wheel
|
||||
|
||||
newcolor.set_red (random() % max_saturation);
|
||||
newcolor.set_blue (random() % max_saturation);
|
||||
newcolor.set_green (random() % max_saturation);
|
||||
|
||||
if (used_colors.size() == 0) {
|
||||
used_colors.push_back (newcolor);
|
||||
return newcolor;
|
||||
}
|
||||
|
||||
for (list<Gdk::Color>::iterator i = used_colors.begin(); i != used_colors.end(); ++i) {
|
||||
Gdk::Color c = *i;
|
||||
float rdelta, bdelta, gdelta;
|
||||
|
||||
rdelta = newcolor.get_red() - c.get_red();
|
||||
bdelta = newcolor.get_blue() - c.get_blue();
|
||||
gdelta = newcolor.get_green() - c.get_green();
|
||||
|
||||
if (sqrt (rdelta*rdelta + bdelta*bdelta + gdelta*gdelta) > 25.0) {
|
||||
used_colors.push_back (newcolor);
|
||||
return newcolor;
|
||||
}
|
||||
}
|
||||
|
||||
/* XXX need throttle here to make sure we don't spin for ever */
|
||||
}
|
||||
return ::unique_random_color (used_colors);
|
||||
}
|
||||
|
||||
string
|
||||
|
|
|
@ -61,7 +61,9 @@ EditorGroupTabs::compute_tabs () const
|
|||
|
||||
tab.from = y;
|
||||
tab.group = g;
|
||||
tab.colour = (*i)->color ();
|
||||
if (g) {
|
||||
tab.color = group_color (g);
|
||||
}
|
||||
}
|
||||
|
||||
y += (*i)->effective_height ();
|
||||
|
@ -81,7 +83,7 @@ EditorGroupTabs::draw_tab (cairo_t* cr, Tab const & tab) const
|
|||
double const arc_radius = _width;
|
||||
|
||||
if (tab.group && tab.group->is_active()) {
|
||||
cairo_set_source_rgba (cr, tab.colour.get_red_p (), tab.colour.get_green_p (), tab.colour.get_blue_p (), 1);
|
||||
cairo_set_source_rgba (cr, tab.color.get_red_p (), tab.color.get_green_p (), tab.color.get_blue_p (), 1);
|
||||
} else {
|
||||
cairo_set_source_rgba (cr, 1, 1, 1, 0.2);
|
||||
}
|
||||
|
|
|
@ -27,12 +27,16 @@
|
|||
#include "group_tabs.h"
|
||||
#include "keyboard.h"
|
||||
#include "i18n.h"
|
||||
#include "ardour_ui.h"
|
||||
#include "utils.h"
|
||||
|
||||
using namespace std;
|
||||
using namespace Gtk;
|
||||
using namespace ARDOUR;
|
||||
using Gtkmm2ext::Keyboard;
|
||||
|
||||
list<Gdk::Color> GroupTabs::_used_colors;
|
||||
|
||||
GroupTabs::GroupTabs ()
|
||||
: _menu (0)
|
||||
, _dragging (0)
|
||||
|
@ -501,3 +505,61 @@ GroupTabs::remove_group (RouteGroup* g)
|
|||
{
|
||||
_session->remove_route_group (*g);
|
||||
}
|
||||
|
||||
/** Set the color of the tab of a route group */
|
||||
void
|
||||
GroupTabs::set_group_color (RouteGroup* group, Gdk::Color color)
|
||||
{
|
||||
assert (group);
|
||||
|
||||
GUIObjectState& gui_state = *ARDOUR_UI::instance()->gui_object_state;
|
||||
|
||||
char buf[64];
|
||||
snprintf (buf, sizeof (buf), "%d:%d:%d", color.get_red(), color.get_green(), color.get_blue());
|
||||
gui_state.set (group_gui_id (group), "color", buf);
|
||||
}
|
||||
|
||||
/** @return the ID string to use for the GUI state of a route group */
|
||||
string
|
||||
GroupTabs::group_gui_id (RouteGroup* group)
|
||||
{
|
||||
assert (group);
|
||||
|
||||
char buf[64];
|
||||
snprintf (buf, sizeof (buf), "route_group %s", group->id().to_s().c_str ());
|
||||
|
||||
return buf;
|
||||
}
|
||||
|
||||
/** @return the color to use for a route group tab */
|
||||
Gdk::Color
|
||||
GroupTabs::group_color (RouteGroup* group)
|
||||
{
|
||||
assert (group);
|
||||
|
||||
GUIObjectState& gui_state = *ARDOUR_UI::instance()->gui_object_state;
|
||||
|
||||
string const gui_id = group_gui_id (group);
|
||||
|
||||
bool empty;
|
||||
string const color = gui_state.get_string (gui_id, "color", &empty);
|
||||
if (empty) {
|
||||
/* no color has yet been set, so use a random one */
|
||||
Gdk::Color const color = unique_random_color (_used_colors);
|
||||
set_group_color (group, color);
|
||||
return color;
|
||||
}
|
||||
|
||||
Gdk::Color c;
|
||||
|
||||
int r, g, b;
|
||||
|
||||
sscanf (color.c_str(), "%d:%d:%d", &r, &g, &b);
|
||||
|
||||
c.set_red (r);
|
||||
c.set_green (g);
|
||||
c.set_blue (b);
|
||||
|
||||
return c;
|
||||
}
|
||||
|
||||
|
|
|
@ -28,7 +28,7 @@ namespace ARDOUR {
|
|||
|
||||
class Editor;
|
||||
|
||||
/** Parent class for tabs which represent route groups as coloured tabs;
|
||||
/** Parent class for tabs which represent route groups as colored tabs;
|
||||
* Currently used on the left-hand side of the editor and at the top of the mixer.
|
||||
*/
|
||||
class GroupTabs : public CairoWidget, public ARDOUR::SessionHandlePtr
|
||||
|
@ -46,6 +46,10 @@ public:
|
|||
|
||||
void run_new_group_dialog (ARDOUR::RouteList const &);
|
||||
|
||||
static void set_group_color (ARDOUR::RouteGroup *, Gdk::Color);
|
||||
static std::string group_gui_id (ARDOUR::RouteGroup *);
|
||||
static Gdk::Color group_color (ARDOUR::RouteGroup *);
|
||||
|
||||
protected:
|
||||
|
||||
struct Tab {
|
||||
|
@ -53,7 +57,7 @@ protected:
|
|||
|
||||
double from;
|
||||
double to;
|
||||
Gdk::Color colour; ///< colour
|
||||
Gdk::Color color; ///< color
|
||||
ARDOUR::RouteGroup* group; ///< route group
|
||||
};
|
||||
|
||||
|
@ -117,4 +121,7 @@ private:
|
|||
double _drag_min; ///< minimum position for drag
|
||||
double _drag_max; ///< maximum position for drag
|
||||
double _drag_first; ///< first mouse pointer position during drag
|
||||
|
||||
/** colors that have been used for new route group tabs */
|
||||
static std::list<Gdk::Color> _used_colors;
|
||||
};
|
||||
|
|
|
@ -67,7 +67,10 @@ MixerGroupTabs::compute_tabs () const
|
|||
|
||||
tab.from = x;
|
||||
tab.group = g;
|
||||
tab.colour = s->color ();
|
||||
|
||||
if (g) {
|
||||
tab.color = group_color (g);
|
||||
}
|
||||
}
|
||||
|
||||
x += s->get_width ();
|
||||
|
@ -87,7 +90,7 @@ MixerGroupTabs::draw_tab (cairo_t* cr, Tab const & tab) const
|
|||
double const arc_radius = _height;
|
||||
|
||||
if (tab.group && tab.group->is_active()) {
|
||||
cairo_set_source_rgba (cr, tab.colour.get_red_p (), tab.colour.get_green_p (), tab.colour.get_blue_p (), 1);
|
||||
cairo_set_source_rgba (cr, tab.color.get_red_p (), tab.color.get_green_p (), tab.color.get_blue_p (), 1);
|
||||
} else {
|
||||
cairo_set_source_rgba (cr, 1, 1, 1, 0.2);
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
#include "ardour/route_group.h"
|
||||
#include "ardour/session.h"
|
||||
#include "route_group_dialog.h"
|
||||
#include "group_tabs.h"
|
||||
#include "i18n.h"
|
||||
#include <iostream>
|
||||
|
||||
|
@ -94,6 +95,7 @@ RouteGroupDialog::RouteGroupDialog (RouteGroup* g, bool creating_new)
|
|||
_select.set_active (_group->is_select());
|
||||
_edit.set_active (_group->is_edit());
|
||||
_route_active.set_active (_group->is_route_active());
|
||||
_color.set_color (GroupTabs::group_color (_group));
|
||||
|
||||
_name.signal_changed().connect (sigc::mem_fun (*this, &RouteGroupDialog::update));
|
||||
_active.signal_toggled().connect (sigc::mem_fun (*this, &RouteGroupDialog::update));
|
||||
|
@ -105,10 +107,11 @@ RouteGroupDialog::RouteGroupDialog (RouteGroup* g, bool creating_new)
|
|||
_select.signal_toggled().connect (sigc::mem_fun (*this, &RouteGroupDialog::update));
|
||||
_edit.signal_toggled().connect (sigc::mem_fun (*this, &RouteGroupDialog::update));
|
||||
_route_active.signal_toggled().connect (sigc::mem_fun (*this, &RouteGroupDialog::update));
|
||||
_color.signal_color_set().connect (sigc::mem_fun (*this, &RouteGroupDialog::update));
|
||||
|
||||
gain_toggled ();
|
||||
|
||||
Table* table = manage (new Table (8, 3, false));
|
||||
Table* table = manage (new Table (11, 4, false));
|
||||
table->set_row_spacings (6);
|
||||
|
||||
l = manage (new Label ("", Gtk::ALIGN_LEFT, Gtk::ALIGN_CENTER, false));
|
||||
|
@ -129,6 +132,12 @@ RouteGroupDialog::RouteGroupDialog (RouteGroup* g, bool creating_new)
|
|||
table->attach (_edit, 1, 3, 7, 8, Gtk::FILL, Gtk::FILL, 0, 0);
|
||||
table->attach (_route_active, 1, 3, 8, 9, Gtk::FILL, Gtk::FILL, 0, 0);
|
||||
|
||||
HBox* b = manage (new HBox);
|
||||
l = manage (new Label (_("Color"), Gtk::ALIGN_LEFT, Gtk::ALIGN_CENTER, false));
|
||||
b->pack_start (*l, Gtk::SHRINK, Gtk::SHRINK);
|
||||
b->pack_start (_color, Gtk::FILL, Gtk::FILL);
|
||||
table->attach (*b, 1, 3, 10, 11, Gtk::FILL, Gtk::FILL, 0, 0);
|
||||
|
||||
options_box->pack_start (*table, false, true);
|
||||
main_vbox->pack_start (*options_box, false, true);
|
||||
|
||||
|
@ -196,6 +205,8 @@ RouteGroupDialog::update ()
|
|||
plist.add (Properties::active, _active.get_active());
|
||||
plist.add (Properties::name, string (_name.get_text()));
|
||||
|
||||
GroupTabs::set_group_color (_group, _color.get_color ());
|
||||
|
||||
_group->apply_changes (plist);
|
||||
}
|
||||
|
||||
|
|
|
@ -23,6 +23,7 @@
|
|||
#include <gtkmm/dialog.h>
|
||||
#include <gtkmm/entry.h>
|
||||
#include <gtkmm/checkbutton.h>
|
||||
#include <gtkmm/colorbutton.h>
|
||||
|
||||
#include "ardour_dialog.h"
|
||||
|
||||
|
@ -48,6 +49,7 @@ private:
|
|||
Gtk::CheckButton _edit;
|
||||
Gtk::CheckButton _route_active;
|
||||
Gtk::Button* _ok;
|
||||
Gtk::ColorButton _color;
|
||||
|
||||
void gain_toggled ();
|
||||
void update ();
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
#include <cstdlib>
|
||||
#include <cctype>
|
||||
#include <fstream>
|
||||
#include <list>
|
||||
#include <sys/stat.h>
|
||||
#include <libart_lgpl/art_misc.h>
|
||||
#include <gtkmm/rc.h>
|
||||
|
@ -938,4 +939,42 @@ escape_underscores (string const & s)
|
|||
return o;
|
||||
}
|
||||
|
||||
Gdk::Color
|
||||
unique_random_color (list<Gdk::Color>& used_colors)
|
||||
{
|
||||
Gdk::Color newcolor;
|
||||
|
||||
while (1) {
|
||||
|
||||
/* avoid neon/glowing tones by limiting them to the
|
||||
"inner section" (paler) of a color wheel/circle.
|
||||
*/
|
||||
|
||||
const int32_t max_saturation = 48000; // 65535 would open up the whole color wheel
|
||||
|
||||
newcolor.set_red (random() % max_saturation);
|
||||
newcolor.set_blue (random() % max_saturation);
|
||||
newcolor.set_green (random() % max_saturation);
|
||||
|
||||
if (used_colors.size() == 0) {
|
||||
used_colors.push_back (newcolor);
|
||||
return newcolor;
|
||||
}
|
||||
|
||||
for (list<Gdk::Color>::iterator i = used_colors.begin(); i != used_colors.end(); ++i) {
|
||||
Gdk::Color c = *i;
|
||||
float rdelta, bdelta, gdelta;
|
||||
|
||||
rdelta = newcolor.get_red() - c.get_red();
|
||||
bdelta = newcolor.get_blue() - c.get_blue();
|
||||
gdelta = newcolor.get_green() - c.get_green();
|
||||
|
||||
if (sqrt (rdelta*rdelta + bdelta*bdelta + gdelta*gdelta) > 25.0) {
|
||||
used_colors.push_back (newcolor);
|
||||
return newcolor;
|
||||
}
|
||||
}
|
||||
|
||||
/* XXX need throttle here to make sure we don't spin for ever */
|
||||
}
|
||||
}
|
||||
|
|
|
@ -91,4 +91,6 @@ void resize_window_to_proportion_of_monitor (Gtk::Window*, int, int);
|
|||
|
||||
std::string escape_underscores (std::string const &);
|
||||
|
||||
Gdk::Color unique_random_color (std::list<Gdk::Color> &);
|
||||
|
||||
#endif /* __ardour_gtk_utils_h__ */
|
||||
|
|
|
@ -213,10 +213,14 @@ RouteGroup::get_max_factor(gain_t factor)
|
|||
}
|
||||
|
||||
XMLNode&
|
||||
RouteGroup::get_state (void)
|
||||
RouteGroup::get_state ()
|
||||
{
|
||||
XMLNode *node = new XMLNode ("RouteGroup");
|
||||
|
||||
char buf[64];
|
||||
id().print (buf, sizeof (buf));
|
||||
node->add_property ("id", buf);
|
||||
|
||||
add_properties (*node);
|
||||
|
||||
if (!routes->empty()) {
|
||||
|
@ -239,10 +243,14 @@ RouteGroup::set_state (const XMLNode& node, int version)
|
|||
return set_state_2X (node, version);
|
||||
}
|
||||
|
||||
set_values (node);
|
||||
|
||||
const XMLProperty *prop;
|
||||
|
||||
if ((prop = node.property ("id")) != 0) {
|
||||
_id = prop->value();
|
||||
}
|
||||
|
||||
set_values (node);
|
||||
|
||||
if ((prop = node.property ("routes")) != 0) {
|
||||
stringstream str (prop->value());
|
||||
vector<string> ids;
|
||||
|
|
Loading…
Reference in New Issue