X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;ds=sidebyside;f=gtk2_ardour%2Ftime_axis_view_item.cc;h=0e66ab2bae2b1372344f565c1572471e7a97df30;hb=cd9fdb935f08966cc8c7170a39870e8adcae69d8;hp=c9fbe922d8db581a8f09b0da8aa2b495b39eefd8;hpb=4c509656223d3ed1f0fab504cb483090d38972f9;p=ardour.git diff --git a/gtk2_ardour/time_axis_view_item.cc b/gtk2_ardour/time_axis_view_item.cc index c9fbe922d8..0e66ab2bae 100644 --- a/gtk2_ardour/time_axis_view_item.cc +++ b/gtk2_ardour/time_axis_view_item.cc @@ -15,36 +15,43 @@ along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - $Id$ */ #include +#include #include #include +#include + #include "public_editor.h" #include "time_axis_view_item.h" #include "time_axis_view.h" -#include "canvas-simplerect.h" -#include "canvas-imageframe.h" +#include "simplerect.h" #include "utils.h" +#include "canvas_impl.h" #include "rgb_macros.h" #include "i18n.h" using namespace std; using namespace Editing; +using namespace Glib; +using namespace PBD; //------------------------------------------------------------------------------ -/** Initialize static memeber data */ -std::string TimeAxisViewItem::NAME_FONT; +/** Initialize const static memeber data */ + +Pango::FontDescription TimeAxisViewItem::NAME_FONT; +bool TimeAxisViewItem::have_name_font = false; const double TimeAxisViewItem::NAME_X_OFFSET = 15.0; -const double TimeAxisViewItem::NAME_Y_OFFSET = 15.0 ; /* XXX depends a lot on the font size, sigh. */ -const double TimeAxisViewItem::NAME_HIGHLIGHT_SIZE = 15.0 ; /* ditto */ -const double TimeAxisViewItem::NAME_HIGHLIGHT_THRESH = 32.0 ; /* ditto */ const double TimeAxisViewItem::GRAB_HANDLE_LENGTH = 6 ; +double TimeAxisViewItem::NAME_Y_OFFSET; +double TimeAxisViewItem::NAME_HIGHLIGHT_SIZE; +double TimeAxisViewItem::NAME_HIGHLIGHT_THRESH; + //---------------------------------------------------------------------------------------// // Constructor / Desctructor @@ -60,82 +67,155 @@ const double TimeAxisViewItem::GRAB_HANDLE_LENGTH = 6 ; * @param start the start point of this item * @param duration the duration of this item */ -TimeAxisViewItem::TimeAxisViewItem(std::string it_name, GnomeCanvasGroup* parent, TimeAxisView& tv, double spu, GdkColor& base_color, - jack_nframes_t start, jack_nframes_t duration, - Visibility visibility) +TimeAxisViewItem::TimeAxisViewItem(const string & it_name, ArdourCanvas::Group& parent, TimeAxisView& tv, double spu, Gdk::Color& base_color, + nframes_t start, nframes_t duration, + Visibility vis) : trackview (tv) { - if (NAME_FONT.empty()) { + if (!have_name_font) { + + /* first constructed item sets up font info */ + NAME_FONT = get_font_for_style (N_("TimeAxisViewItemName")); + + Gtk::Window win; + Gtk::Label foo; + win.add (foo); + + Glib::RefPtr layout = foo.create_pango_layout (X_("Hg")); /* ascender + descender */ + int width; + int height; + + layout->set_font_description (NAME_FONT); + Gtkmm2ext::get_ink_pixel_size (layout, width, height); + + NAME_Y_OFFSET = height + 6; + NAME_HIGHLIGHT_SIZE = height + 6; + NAME_HIGHLIGHT_THRESH = NAME_HIGHLIGHT_SIZE * 2; + + have_name_font = true; } + group = new ArdourCanvas::Group (parent); + + init (it_name, spu, base_color, start, duration, vis); + +} + +TimeAxisViewItem::TimeAxisViewItem (const TimeAxisViewItem& other) + : trackview (other.trackview) +{ + + Gdk::Color c; + int r,g,b,a; + + UINT_TO_RGBA (other.fill_color, &r, &g, &b, &a); + c.set_rgb_p (r/255.0, g/255.0, b/255.0); + + /* share the other's parent, but still create a new group */ + + Gnome::Canvas::Group* parent = other.group->property_parent(); + + group = new ArdourCanvas::Group (*parent); + + init (other.item_name, other.samples_per_unit, c, other.frame_position, other.item_duration, other.visibility); +} + + +void +TimeAxisViewItem::init (const string& it_name, double spu, Gdk::Color& base_color, nframes_t start, nframes_t duration, Visibility vis) +{ item_name = it_name ; + name_text_width = ::pixel_width (it_name, NAME_FONT); + last_name_text_width = 0; samples_per_unit = spu ; should_show_selection = true; frame_position = start ; item_duration = duration ; name_connected = false; - fill_opacity = 50; + fill_opacity = 60; position_locked = false ; max_item_duration = ARDOUR::max_frames; min_item_duration = 0 ; show_vestigial = true; + visibility = vis; + _sensitive = true; if (duration == 0) { warning << "Time Axis Item Duration == 0" << endl ; } - group = gnome_canvas_item_new(GNOME_CANVAS_GROUP(parent),gnome_canvas_group_get_type(),NULL) ; - - vestigial_frame = gnome_canvas_item_new(GNOME_CANVAS_GROUP(group), - gnome_canvas_simplerect_get_type(), - "x1", (double) 0.0, - "y1", (double) 1.0, - "x2", 2.0, - "y2", (double) trackview.height, - "outline_color_rgba", color_map[cVestigialFrameOutline], - "fill_color_rgba", color_map[cVestigialFrameFill], - NULL); - gnome_canvas_item_hide (vestigial_frame); + vestigial_frame = new ArdourCanvas::SimpleRect (*group); + vestigial_frame->property_x1() = (double) 0.0; + vestigial_frame->property_y1() = (double) 1.0; + vestigial_frame->property_x2() = 2.0; + vestigial_frame->property_y2() = (double) trackview.height; + vestigial_frame->property_outline_color_rgba() = color_map[cVestigialFrameOutline]; + vestigial_frame->property_fill_color_rgba() = color_map[cVestigialFrameFill]; + vestigial_frame->hide (); if (visibility & ShowFrame) { - frame = gnome_canvas_item_new(GNOME_CANVAS_GROUP(group), - gnome_canvas_simplerect_get_type(), - "x1", (double) 0.0, - "y1", (double) 1.0, - "x2", (double) trackview.editor.frame_to_pixel(duration), - "y2", (double) trackview.height, - "outline_color_rgba", color_map[cTimeAxisFrameOutline], - "fill_color_rgba", color_map[cTimeAxisFrameFill], - NULL); + frame = new ArdourCanvas::SimpleRect (*group); + frame->property_x1() = (double) 0.0; + frame->property_y1() = (double) 1.0; + frame->property_x2() = (double) trackview.editor.frame_to_pixel(duration); + frame->property_y2() = (double) trackview.height; + frame->property_outline_color_rgba() = color_map[cTimeAxisFrameOutline]; + frame->property_fill_color_rgba() = color_map[cTimeAxisFrameFill]; + + /* by default draw all 4 edges */ + + uint32_t outline_what = 0x1|0x2|0x4|0x8; + + if (visibility & HideFrameLeft) { + outline_what &= ~(0x1); + } + + if (visibility & HideFrameRight) { + outline_what &= ~(0x2); + } + + if (visibility & HideFrameTB) { + outline_what &= ~(0x4 | 0x8); + } + + frame->property_outline_what() = outline_what; + } else { frame = 0; } if (visibility & ShowNameHighlight) { - name_highlight = gnome_canvas_item_new(GNOME_CANVAS_GROUP(group), - gnome_canvas_simplerect_get_type(), - "x1", (double) 1.0, - "x2", (double) (trackview.editor.frame_to_pixel(item_duration)) - 1, - "y1", (double) (trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE), - "y2", (double) (trackview.height - 1), - "outline_color_rgba", color_map[cNameHighlightFill], - "fill_color_rgba", color_map[cNameHighlightOutline], - NULL) ; - gtk_object_set_data(GTK_OBJECT(name_highlight), "timeaxisviewitem", this) ; + name_highlight = new ArdourCanvas::SimpleRect (*group); + if (visibility & FullWidthNameHighlight) { + name_highlight->property_x1() = (double) 0.0; + name_highlight->property_x2() = (double) (trackview.editor.frame_to_pixel(item_duration)); + } else { + name_highlight->property_x1() = (double) 1.0; + name_highlight->property_x2() = (double) (trackview.editor.frame_to_pixel(item_duration)) - 1; + } + name_highlight->property_y1() = (double) (trackview.height - TimeAxisViewItem::NAME_HIGHLIGHT_SIZE); + name_highlight->property_y2() = (double) (trackview.height - 1); + name_highlight->property_outline_color_rgba() = color_map[cNameHighlightFill]; + name_highlight->property_fill_color_rgba() = color_map[cNameHighlightOutline]; + + name_highlight->set_data ("timeaxisviewitem", this); + } else { name_highlight = 0; } if (visibility & ShowNameText) { - name_text = gnome_canvas_item_new(GNOME_CANVAS_GROUP(group), - gnome_canvas_text_get_type(), - "x", (double) TimeAxisViewItem::NAME_X_OFFSET, - "y", (double) trackview.height + 1.0 - TimeAxisViewItem::NAME_Y_OFFSET, - "font", NAME_FONT.c_str(), - "anchor", GTK_ANCHOR_NW, - NULL) ; - gtk_object_set_data(GTK_OBJECT(name_text), "timeaxisviewitem", this) ; + name_text = new ArdourCanvas::Text (*group); + name_text->property_x() = (double) TimeAxisViewItem::NAME_X_OFFSET; + /* trackview.height is the bottom of the trackview. subtract 1 to get back to the bottom of the highlight, + then NAME_Y_OFFSET to position the text in the vertical center of the highlight + */ + name_text->property_y() = (double) trackview.height - 1.0 - TimeAxisViewItem::NAME_Y_OFFSET; + name_text->property_font_desc() = NAME_FONT; + name_text->property_anchor() = Gtk::ANCHOR_NW; + + name_text->set_data ("timeaxisviewitem", this); } else { name_text = 0; @@ -144,25 +224,22 @@ TimeAxisViewItem::TimeAxisViewItem(std::string it_name, GnomeCanvasGroup* parent /* create our grab handles used for trimming/duration etc */ if (visibility & ShowHandles) { - frame_handle_start = gnome_canvas_item_new(GNOME_CANVAS_GROUP(group), - gnome_canvas_simplerect_get_type(), - "x1", (double) 0.0, - "x2", (double) TimeAxisViewItem::GRAB_HANDLE_LENGTH, - "y1", (double) 1.0, - "y2", (double) TimeAxisViewItem::GRAB_HANDLE_LENGTH+1, - "outline_color_rgba", color_map[cFrameHandleStartOutline], - "fill_color_rgba", color_map[cFrameHandleStartFill], - NULL) ; + frame_handle_start = new ArdourCanvas::SimpleRect (*group); + frame_handle_start->property_x1() = (double) 0.0; + frame_handle_start->property_x2() = (double) TimeAxisViewItem::GRAB_HANDLE_LENGTH; + frame_handle_start->property_y1() = (double) 1.0; + frame_handle_start->property_y2() = (double) TimeAxisViewItem::GRAB_HANDLE_LENGTH+1; + frame_handle_start->property_outline_color_rgba() = color_map[cFrameHandleStartOutline]; + frame_handle_start->property_fill_color_rgba() = color_map[cFrameHandleStartFill]; - frame_handle_end = gnome_canvas_item_new(GNOME_CANVAS_GROUP(group), - gnome_canvas_simplerect_get_type(), - "x1", (double) (trackview.editor.frame_to_pixel(get_duration())) - (TimeAxisViewItem::GRAB_HANDLE_LENGTH), - "x2", (double) trackview.editor.frame_to_pixel(get_duration()), - "y1", (double) 1, - "y2", (double) TimeAxisViewItem::GRAB_HANDLE_LENGTH + 1, - "outline_color_rgba", color_map[cFrameHandleEndOutline], - "fill_color_rgba", color_map[cFrameHandleEndFill], - NULL) ; + frame_handle_end = new ArdourCanvas::SimpleRect (*group); + frame_handle_end->property_x1() = (double) (trackview.editor.frame_to_pixel(get_duration())) - (TimeAxisViewItem::GRAB_HANDLE_LENGTH); + frame_handle_end->property_x2() = (double) trackview.editor.frame_to_pixel(get_duration()); + frame_handle_end->property_y1() = (double) 1; + frame_handle_end->property_y2() = (double) TimeAxisViewItem::GRAB_HANDLE_LENGTH + 1; + frame_handle_end->property_outline_color_rgba() = color_map[cFrameHandleEndOutline]; + frame_handle_end->property_fill_color_rgba() = color_map[cFrameHandleEndFill]; + } else { frame_handle_start = 0; frame_handle_end = 0; @@ -174,13 +251,12 @@ TimeAxisViewItem::TimeAxisViewItem(std::string it_name, GnomeCanvasGroup* parent set_position (start, this) ; } - /** * Destructor */ TimeAxisViewItem::~TimeAxisViewItem() { - gtk_object_destroy (GTK_OBJECT(group)); + delete group; } @@ -195,7 +271,7 @@ TimeAxisViewItem::~TimeAxisViewItem() * @return true if the position change was a success, false otherwise */ bool -TimeAxisViewItem::set_position(jack_nframes_t pos, void* src, double* delta) +TimeAxisViewItem::set_position(nframes_t pos, void* src, double* delta) { if (position_locked) { return false; @@ -212,23 +288,20 @@ TimeAxisViewItem::set_position(jack_nframes_t pos, void* src, double* delta) version of GNOME Canvas rectifies this issue cleanly. */ - GtkArg args[1] ; double old_unit_pos ; double new_unit_pos = pos / samples_per_unit ; - args[0].name = "x" ; - gtk_object_getv (GTK_OBJECT(group), 1, args) ; - old_unit_pos = GTK_VALUE_DOUBLE (args[0]) ; + old_unit_pos = group->property_x(); if (new_unit_pos != old_unit_pos) { - gnome_canvas_item_move (group, new_unit_pos - old_unit_pos, 0.0) ; + group->move (new_unit_pos - old_unit_pos, 0.0); } - + if (delta) { (*delta) = new_unit_pos - old_unit_pos; } - PositionChanged (frame_position, src) ; /* EMIT_SIGNAL */ + PositionChanged (frame_position, src) ; /* EMIT_SIGNAL */ return true; } @@ -238,7 +311,7 @@ TimeAxisViewItem::set_position(jack_nframes_t pos, void* src, double* delta) * * @return the position of this item */ -jack_nframes_t +nframes_t TimeAxisViewItem::get_position() const { return frame_position; @@ -252,7 +325,7 @@ TimeAxisViewItem::get_position() const * @return true if the duration change was succesful, false otherwise */ bool -TimeAxisViewItem::set_duration (jack_nframes_t dur, void* src) +TimeAxisViewItem::set_duration (nframes_t dur, void* src) { if ((dur > max_item_duration) || (dur < min_item_duration)) { warning << string_compose (_("new duration %1 frames is out of bounds for %2"), get_item_name(), dur) @@ -261,16 +334,14 @@ TimeAxisViewItem::set_duration (jack_nframes_t dur, void* src) } if (dur == 0) { - gnome_canvas_item_hide (group); + group->hide(); } item_duration = dur; - double pixel_width = trackview.editor.frame_to_pixel (dur); - - reset_width_dependent_items (pixel_width); + reset_width_dependent_items (trackview.editor.frame_to_pixel (dur)); - DurationChanged (dur, src) ; /* EMIT_SIGNAL */ + DurationChanged (dur, src) ; /* EMIT_SIGNAL */ return true; } @@ -278,7 +349,7 @@ TimeAxisViewItem::set_duration (jack_nframes_t dur, void* src) * Returns the duration of this item * */ -jack_nframes_t +nframes_t TimeAxisViewItem::get_duration() const { return (item_duration); @@ -291,10 +362,10 @@ TimeAxisViewItem::get_duration() const * @param src the identity of the object that initiated the change */ void -TimeAxisViewItem::set_max_duration(jack_nframes_t dur, void* src) +TimeAxisViewItem::set_max_duration(nframes_t dur, void* src) { max_item_duration = dur ; - MaxDurationChanged(max_item_duration, src) ; /* EMIT_SIGNAL */ + MaxDurationChanged(max_item_duration, src) ; /* EMIT_SIGNAL */ } /** @@ -302,10 +373,10 @@ TimeAxisViewItem::set_max_duration(jack_nframes_t dur, void* src) * * @return the maximum duration that this item may be set to */ -jack_nframes_t +nframes_t TimeAxisViewItem::get_max_duration() const { - return(max_item_duration) ; + return (max_item_duration) ; } /** @@ -315,10 +386,10 @@ TimeAxisViewItem::get_max_duration() const * @param src the identity of the object that initiated the change */ void -TimeAxisViewItem::set_min_duration(jack_nframes_t dur, void* src) +TimeAxisViewItem::set_min_duration(nframes_t dur, void* src) { min_item_duration = dur ; - MinDurationChanged(max_item_duration, src) ; /* EMIT_SIGNAL */ + MinDurationChanged(max_item_duration, src) ; /* EMIT_SIGNAL */ } /** @@ -326,7 +397,7 @@ TimeAxisViewItem::set_min_duration(jack_nframes_t dur, void* src) * * @return the nimum duration that this item mey be set to */ -jack_nframes_t +nframes_t TimeAxisViewItem::get_min_duration() const { return(min_item_duration) ; @@ -420,6 +491,7 @@ TimeAxisViewItem::set_item_name(std::string new_name, void* src) if (new_name != item_name) { std::string temp_name = item_name ; item_name = new_name ; + name_text_width = ::pixel_width (new_name, NAME_FONT); NameChanged (item_name, temp_name, src) ; /* EMIT_SIGNAL */ } } @@ -445,26 +517,14 @@ TimeAxisViewItem::get_item_name() const * @param src the identity of the object that initiated the change */ void -TimeAxisViewItem::set_selected(bool yn, void* src) +TimeAxisViewItem::set_selected(bool yn) { if (_selected != yn) { - _selected = yn ; + Selectable::set_selected (yn); set_frame_color (); - Selected (_selected) ; /* EMIT_SIGNAL */ } } -/** - * Returns whether this item is currently selected. - * - * @return true if this item is currently selected, false otherwise - */ -bool -TimeAxisViewItem::get_selected() const -{ - return (_selected) ; -} - void TimeAxisViewItem::set_should_show_selection (bool yn) { @@ -497,67 +557,72 @@ TimeAxisViewItem::get_time_axis_view() * @param new_name the new name text to display */ void -TimeAxisViewItem::set_name_text(std::string new_name) +TimeAxisViewItem::set_name_text(const ustring& new_name) { if (name_text) { - gnome_canvas_item_set (name_text, "text", new_name.c_str(), NULL); + name_text->property_text() = new_name; + name_text_width = pixel_width (new_name, NAME_FONT); + name_text_size_cache.clear (); } } /** - * Set the height of this item + * Set the y position and height of this item. * + * @param y the new y position * @param h the new height */ void -TimeAxisViewItem::set_height(double height) +TimeAxisViewItem::set_y_position_and_height (double y, double h) { if (name_highlight) { - if (height < NAME_HIGHLIGHT_THRESH) { - gnome_canvas_item_hide (name_highlight); - gnome_canvas_item_hide (name_text); + if (h < NAME_HIGHLIGHT_THRESH) { + name_highlight->hide(); + if (name_text) { + name_text->hide(); + } } else { - gnome_canvas_item_show (name_highlight); - gnome_canvas_item_show (name_text); + name_highlight->show(); + if (name_text) { + name_text->show(); + } } - if (height > NAME_HIGHLIGHT_SIZE) { - gnome_canvas_item_set (name_highlight, - "y1", (double) height+1 - NAME_HIGHLIGHT_SIZE, - "y2", (double) height, - NULL); + if (h > NAME_HIGHLIGHT_SIZE) { + name_highlight->property_y1() = (double) y + h + 1 - NAME_HIGHLIGHT_SIZE; + name_highlight->property_y2() = (double) y + h; } else { /* it gets hidden now anyway */ - gnome_canvas_item_set (name_highlight, - "y1", (double) 1.0, - "y2", (double) height, - NULL); + name_highlight->property_y1() = (double) y; + name_highlight->property_y2() = (double) y + h; } } if (name_text) { - gnome_canvas_item_set (name_text, "y", height+1 - NAME_Y_OFFSET, NULL); - if (height < NAME_HIGHLIGHT_THRESH) { - gnome_canvas_item_set(name_text, "fill_color_rgba", fill_color, NULL) ; + name_text->property_y() = y + h + 1 - NAME_Y_OFFSET; + if (h < NAME_HIGHLIGHT_THRESH) { + name_text->property_fill_color_rgba() = fill_color; } else { - gnome_canvas_item_set(name_text, "fill_color_rgba", label_color, NULL) ; + name_text->property_fill_color_rgba() = label_color; } } if (frame) { - gnome_canvas_item_set (frame, "y2", height+1, NULL) ; + frame->property_y1() = y; + frame->property_y2() = y + h + 1; } - gnome_canvas_item_set (vestigial_frame, "y2", height+1, NULL) ; + vestigial_frame->property_y1() = y; + vestigial_frame->property_y2() = y + h + 1; } /** * */ void -TimeAxisViewItem::set_color(GdkColor& base_color) +TimeAxisViewItem::set_color(Gdk::Color& base_color) { compute_colors (base_color); set_colors (); @@ -566,7 +631,7 @@ TimeAxisViewItem::set_color(GdkColor& base_color) /** * */ -GnomeCanvasItem* +ArdourCanvas::Item* TimeAxisViewItem::get_canvas_frame() { return(frame) ; @@ -575,28 +640,28 @@ TimeAxisViewItem::get_canvas_frame() /** * */ -GnomeCanvasItem* +ArdourCanvas::Item* TimeAxisViewItem::get_canvas_group() { - return(group) ; + return (group) ; } /** * */ -GnomeCanvasItem* +ArdourCanvas::Item* TimeAxisViewItem::get_name_highlight() { - return(name_highlight) ; + return (name_highlight) ; } /** * */ -GnomeCanvasItem* +ArdourCanvas::Text* TimeAxisViewItem::get_name_text() { - return(name_text) ; + return (name_text) ; } /** @@ -605,7 +670,7 @@ TimeAxisViewItem::get_name_text() * @param color the base color of the item */ void -TimeAxisViewItem::compute_colors(GdkColor& base_color) +TimeAxisViewItem::compute_colors(Gdk::Color& base_color) { unsigned char radius ; char minor_shift ; @@ -613,9 +678,9 @@ TimeAxisViewItem::compute_colors(GdkColor& base_color) unsigned char r,g,b ; /* FILL: this is simple */ - r = base_color.red/256 ; - g = base_color.green/256 ; - b = base_color.blue/256 ; + r = base_color.get_red()/256 ; + g = base_color.get_green()/256 ; + b = base_color.get_blue()/256 ; fill_color = RGBA_TO_UINT(r,g,b,255) ; /* for minor colors: @@ -631,9 +696,9 @@ TimeAxisViewItem::compute_colors(GdkColor& base_color) /* LABEL: rotate around color wheel by 120 degrees anti-clockwise */ - r = base_color.red/256; - g = base_color.green/256; - b = base_color.blue/256; + r = base_color.get_red()/256; + g = base_color.get_green()/256; + b = base_color.get_blue()/256; if (r > b) { @@ -667,9 +732,9 @@ TimeAxisViewItem::compute_colors(GdkColor& base_color) g += minor_shift; label_color = RGBA_TO_UINT(r,g,b,255); - r = (base_color.red/256) + 127 ; - g = (base_color.green/256) + 127 ; - b = (base_color.blue/256) + 127 ; + r = (base_color.get_red()/256) + 127 ; + g = (base_color.get_green()/256) + 127 ; + b = (base_color.get_blue()/256) + 127 ; label_color = RGBA_TO_UINT(r,g,b,255); @@ -704,23 +769,20 @@ TimeAxisViewItem::set_colors() double height = NAME_HIGHLIGHT_THRESH; if (frame) { - GtkArg args[1] ; - args[0].name = "y2" ; - gtk_object_getv (GTK_OBJECT(frame), 1, args); - height = GTK_VALUE_DOUBLE (args[0]); + height = frame->property_y2(); } if (height < NAME_HIGHLIGHT_THRESH) { - gnome_canvas_item_set(name_text, "fill_color_rgba", fill_color, NULL) ; + name_text->property_fill_color_rgba() = fill_color; } else { - gnome_canvas_item_set(name_text, "fill_color_rgba", label_color, NULL) ; + name_text->property_fill_color_rgba() = label_color; } } if (name_highlight) { - gnome_canvas_item_set(name_highlight, "fill_color_rgba", fill_color, NULL) ; - gnome_canvas_item_set(name_highlight, "outline_color_rgba", fill_color, NULL) ; + name_highlight->property_fill_color_rgba() = fill_color; + name_highlight->property_outline_color_rgba() = fill_color; } set_trim_handle_colors() ; } @@ -736,10 +798,10 @@ TimeAxisViewItem::set_frame_color() if (_selected && should_show_selection) { UINT_TO_RGBA(color_map[cSelectedFrameBase], &r, &g, &b, &a); - gnome_canvas_item_set(frame, "fill_color_rgba", RGBA_TO_UINT(r, g, b, fill_opacity), NULL) ; + frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, fill_opacity); } else { UINT_TO_RGBA(color_map[cFrameBase], &r, &g, &b, &a); - gnome_canvas_item_set(frame, "fill_color_rgba", RGBA_TO_UINT(r, g, b, fill_opacity), NULL) ; + frame->property_fill_color_rgba() = RGBA_TO_UINT(r, g, b, fill_opacity); } } } @@ -753,11 +815,11 @@ TimeAxisViewItem::set_trim_handle_colors() { if (frame_handle_start) { if (position_locked) { - gnome_canvas_item_set(frame_handle_start, "fill_color_rgba", color_map[cTrimHandleLockedStart], NULL); - gnome_canvas_item_set(frame_handle_end, "fill_color_rgba", color_map[cTrimHandleLockedEnd], NULL) ; + frame_handle_start->property_fill_color_rgba() = color_map[cTrimHandleLockedStart]; + frame_handle_end->property_fill_color_rgba() = color_map[cTrimHandleLockedEnd]; } else { - gnome_canvas_item_set(frame_handle_start, "fill_color_rgba", color_map[cTrimHandleStart], NULL) ; - gnome_canvas_item_set(frame_handle_end, "fill_color_rgba", color_map[cTrimHandleEnd], NULL) ; + frame_handle_start->property_fill_color_rgba() = color_map[cTrimHandleStart]; + frame_handle_end->property_fill_color_rgba() = color_map[cTrimHandleEnd]; } } } @@ -782,66 +844,74 @@ TimeAxisViewItem::reset_width_dependent_items (double pixel_width) if (pixel_width < GRAB_HANDLE_LENGTH * 2) { if (frame_handle_start) { - gnome_canvas_item_hide (frame_handle_start); - gnome_canvas_item_hide (frame_handle_end); + frame_handle_start->hide(); + frame_handle_end->hide(); } } if (pixel_width < 2.0) { if (show_vestigial) { - gnome_canvas_item_show (vestigial_frame); + vestigial_frame->show(); } if (name_highlight) { - gnome_canvas_item_hide (name_highlight); - gnome_canvas_item_hide (name_text); + name_highlight->hide(); + if (name_text) { + name_text->hide(); + } } if (frame) { - gnome_canvas_item_hide (frame); + frame->hide(); } if (frame_handle_start) { - gnome_canvas_item_hide (frame_handle_start); - gnome_canvas_item_hide (frame_handle_end); + frame_handle_start->hide(); + frame_handle_end->hide(); } } else { - gnome_canvas_item_hide (vestigial_frame); + vestigial_frame->hide(); if (name_highlight) { - GtkArg args[1] ; - args[0].name = "y2" ; - gtk_object_getv (GTK_OBJECT(name_highlight), 1, args); - double height = GTK_VALUE_DOUBLE (args[0]); + double height = name_highlight->property_y2 (); if (height < NAME_HIGHLIGHT_THRESH) { - gnome_canvas_item_hide (name_highlight); - gnome_canvas_item_hide (name_text); + name_highlight->hide(); + if (name_text) { + name_text->hide(); + } + } else { + name_highlight->show(); + if (name_text && !get_item_name().empty()) { + name_text->show(); + reset_name_width (pixel_width); + } + } + + if (visibility & FullWidthNameHighlight) { + name_highlight->property_x2() = pixel_width; } else { - gnome_canvas_item_show (name_highlight); - gnome_canvas_item_show (name_text); - reset_name_width (pixel_width); + name_highlight->property_x2() = pixel_width - 1.0; } - gnome_canvas_item_set (name_highlight, "x2", pixel_width - 1.0, NULL); } if (frame) { - gnome_canvas_item_show (frame); - gnome_canvas_item_set (frame, "x2", pixel_width, NULL); + frame->show(); + frame->property_x2() = pixel_width; } if (frame_handle_start) { if (pixel_width < (2*TimeAxisViewItem::GRAB_HANDLE_LENGTH)) { - gnome_canvas_item_hide (frame_handle_start); - gnome_canvas_item_hide (frame_handle_end); + frame_handle_start->hide(); + frame_handle_end->hide(); } - gnome_canvas_item_show (frame_handle_start); - gnome_canvas_item_set(GNOME_CANVAS_ITEM(frame_handle_end), "x1", pixel_width - (TimeAxisViewItem::GRAB_HANDLE_LENGTH ), NULL) ; - gnome_canvas_item_show (frame_handle_end); - gnome_canvas_item_set(GNOME_CANVAS_ITEM(frame_handle_end), "x2", pixel_width, NULL) ; + frame_handle_start->show(); + frame_handle_end->property_x1() = pixel_width - (TimeAxisViewItem::GRAB_HANDLE_LENGTH); + frame_handle_end->show(); + frame_handle_end->property_x2() = pixel_width; } } } @@ -849,63 +919,90 @@ TimeAxisViewItem::reset_width_dependent_items (double pixel_width) void TimeAxisViewItem::reset_name_width (double pixel_width) { - gint width; - gint lbearing; - gint rbearing; - gint ascent; - gint descent; - Gdk_Font font (NAME_FONT); - if (name_text == 0) { return; } - int namelen = item_name.length(); - char cstr[namelen+1]; - strcpy (cstr, item_name.c_str()); - - while (namelen) { - - gdk_string_extents (font, - cstr, - &lbearing, - &rbearing, - &width, - &ascent, - &descent); - - if (width < (pixel_width - NAME_X_OFFSET)) { - break; - } + int limit = (int) floor (pixel_width - NAME_X_OFFSET); + bool shrinking = (last_name_text_width > pixel_width); + int actual_width; + ustring ustr; + ustring::size_type n; + + if ((last_name_text_width && // we did this once + shrinking && // we're getting smaller + (name_text_width <= limit) && // fits the new size + (name_text_width <= last_name_text_width - NAME_X_OFFSET))) { // fit into the old size too + last_name_text_width = pixel_width; + return; + } - --namelen; - cstr[namelen] = '\0'; + /* now check the cache of existing truncations */ - } + Gtk::Label foo; + Glib::RefPtr layout = foo.create_pango_layout (""); - if (namelen == 0) { - - gnome_canvas_item_hide (name_text); + for (n = item_name.length(); n > 0; --n) { - } else { - - /* don't use name for event handling if it leaves no room - for trimming to work. - */ - - if (pixel_width - width < (NAME_X_OFFSET * 2.0)) { - if (name_connected) { - name_connected = false; + map::iterator i; + + if ((i = name_text_size_cache.find (n)) != name_text_size_cache.end()) { + + /* we know the length of this substring already */ + + if ((actual_width = (*i).second) < limit) { + + /* it fits, use it */ + + ustr = item_name.substr (0, n); + break; } + } else { - if (!name_connected) { - name_connected = true; + + /* we don't know the length of this substring already, so compute + it and put it into the cache. + */ + + layout->set_text (item_name.substr (0, n)); + + int width, height; + Gtkmm2ext::get_ink_pixel_size (layout, width, height); + + name_text_size_cache[n] = width; + + if ((actual_width = width) < limit) { + ustr = item_name.substr (0, n); + break; } } - - gnome_canvas_item_set (name_text, "text", cstr, NULL); - gnome_canvas_item_show (name_text); } + + if (n == 0) { + name_text->property_text() = ""; + last_name_text_width = pixel_width; + return; + } + + /* don't use name for event handling if it leaves no room + for trimming to work. + */ + + if (pixel_width - actual_width < (NAME_X_OFFSET * 2.0)) { + if (name_connected) { + name_connected = false; + } + } else { + if (!name_connected) { + name_connected = true; + } + } + + name_text->property_text() = ustr; + name_text_width = actual_width; + name_text->show(); + last_name_text_width = pixel_width; + } @@ -929,7 +1026,7 @@ TimeAxisViewItem::remove_this_item(void* src) defer to idle loop, otherwise we'll delete this object while we're still inside this function ... */ - Gtk::Main::idle.connect(bind(mem_fun(&TimeAxisViewItem::idle_remove_this_item), this, src)); + Glib::signal_idle().connect(bind (sigc::ptr_fun (&TimeAxisViewItem::idle_remove_this_item), this, src)); } /** @@ -937,14 +1034,14 @@ TimeAxisViewItem::remove_this_item(void* src) * This is used to avoid deleting the obejct while inside the remove_this_item * method * - * @param item the ImageFrameTimeAxisGroup to remove + * @param item the TimeAxisViewItem to remove * @param src the identity of the object that initiated the change */ gint TimeAxisViewItem::idle_remove_this_item(TimeAxisViewItem* item, void* src) { - item->ItemRemoved(item->get_item_name(), src) ; /* EMIT_SIGNAL */ - delete item ; - item = 0 ; - return(false) ; + item->ItemRemoved (item->get_item_name(), src) ; /* EMIT_SIGNAL */ + delete item; + item = 0; + return false; }