changes from 2.X starting in march 2009 through oct 20 2009 (5826 inclusive)

git-svn-id: svn://localhost/ardour2/branches/3.0@6761 d708f5d6-7413-0410-9779-e7cbd77b26cf
This commit is contained in:
Paul Davis
2010-03-16 15:33:04 +00:00
parent 830911f6f9
commit 6ef5d85ae1
54 changed files with 703 additions and 204 deletions

View File

@@ -1,15 +1,12 @@
(1) VST SUPPORT
You may not distribute binaries of Ardour with VST support. Doing so
is a violation of the license agreement for the Steinberg VST SDK. If
you are found to be distributing such binaries, you risk both
prosecution by Steinberg and public humiliation by me.
This is not my choice, and as soon as Steinberg change their
licensing, which they have indicated they will do, this policy (and
file) will be removed.
Please do not distribution Ardour with VST support under the package
name "ardour" (or any case-variant on that). Use some other name such
as "ardourvst", "ArdourVST", "ardour-vst" etc. In the near future,
work will be done to make it possible to share as much as possible of
the packaging.
(2) STANDARD TEMPLATES
The templates in ./templates are intended for installation in
$prefix/share/ardour3/templates.
$prefix/share/ardour2/templates.

2
README
View File

@@ -1,3 +1,3 @@
Please see the Ardour web site at http://ardour.org/ for all documentation..
For information on building ardour: http://ardour.org/building.

View File

@@ -156,6 +156,7 @@ static const char* authors[] = {
N_("Nimal Ratnayake"),
N_("Dave Robillard"),
N_("Taybin Rutkin"),
N_("Andreas Ruge"),
N_("Sampo Savolainen"),
N_("Per Sigmond"),
N_("Lincoln Spiteri"),
@@ -168,7 +169,7 @@ static const char* authors[] = {
};
static const char* translators[] = {
N_("French:\n\tAlain Fréhel <alain.frehel@free.fr>\n\tChristophe Combelles <ccomb@free.fr>\n"),
N_("French:\n\tAlain Fréhel <alain.frehel@free.fr>\n\tChristophe Combelles <ccomb@free.fr>\n\tMartin Blanchard\n"),
N_("German:\n\tKarsten Petersen <kapet@kapet.de>\
\n\tSebastian Arnold <mail@sebastian-arnold.net>\
\n\tRobert Schwede<schwede@ironshark.com>\n"),
@@ -181,6 +182,8 @@ static const char* translators[] = {
N_("Greek:\n\t Klearchos Gourgourinis <muadib@in.gr>\n"),
N_("Swedish:\n\t Petter Sundlöf <petter.sundlof@gmail.com>\n"),
N_("Polish:\n\t Piotr Zaryk <pzaryk@gmail.com>\n"),
N_("Czech:\n\t Pavel Frich\n"),
N_("Norwegian:\n\t Eivind Ødegård\n"),
0
};
@@ -559,7 +562,7 @@ About::About ()
}
set_translator_credits (t);
set_copyright (_("Copyright (C) 1999-2009 Paul Davis\n"));
set_copyright (_("Copyright (C) 1999-2010 Paul Davis\n"));
set_license (gpl);
set_name (X_("ardour"));
set_website (X_("http://ardour.org/"));

View File

@@ -286,6 +286,7 @@
<menuitem action='track-height-smaller'/>
<menuitem action='track-height-small'/>
</menu>
<menuitem action='track-record-enable-toggle'/>
<menuitem action='toggle-track-active'/>
<menuitem action='remove-track'/>
</menu>
@@ -433,7 +434,10 @@
<separator/>
</menu>
<menu name='Help' action='Help'>
#ifndef GTKOSX
<menuitem action='About'/>
#endif
<menuitem action='Chat'/>
</menu>
</menubar>

View File

@@ -42,6 +42,7 @@
#include "pbd/failed_constructor.h"
#include "pbd/enumwriter.h"
#include "pbd/memento_command.h"
#include "pbd/openuri.h"
#include "pbd/file_utils.h"
#include "gtkmm2ext/gtk_ui.h"
@@ -2036,6 +2037,7 @@ ARDOUR_UI::snapshot_session ()
prompter.set_prompt (_("Name of New Snapshot"));
prompter.set_initial_text (timebuf);
again:
switch (prompter.run()) {
case RESPONSE_ACCEPT:
{
@@ -2043,6 +2045,21 @@ ARDOUR_UI::snapshot_session ()
bool do_save = (snapname.length() != 0);
if (do_save) {
if (snapname.find ('/') != string::npos) {
MessageDialog msg (_("To ensure compatibility with various systems\n"
"snapshot names may not contain a '/' character"));
msg.run ();
goto again;
}
if (snapname.find ('\\') != string::npos) {
MessageDialog msg (_("To ensure compatibility with various systems\n"
"snapshot names may not contain a '\\' character"));
msg.run ();
goto again;
}
}
vector<sys::path> p;
get_state_files_in_directory (_session->session_directory().root_path(), p);
vector<string> n = get_file_names_no_extension (p);
@@ -2493,6 +2510,10 @@ ARDOUR_UI::get_session_parameters (bool quit_on_cancel, bool should_be_new)
(session_name.length() > 2 && session_name[0] == '.' && session_name[1] == '/') ||
(session_name.length() > 3 && session_name[0] == '.' && session_name[1] == '.' && session_name[2] == '/')) {
/* absolute path or cwd-relative path specified for session name: infer session folder
from what was given.
*/
session_path = Glib::path_get_dirname (session_name);
session_name = Glib::path_get_basename (session_name);
@@ -2529,6 +2550,22 @@ ARDOUR_UI::get_session_parameters (bool quit_on_cancel, bool should_be_new)
continue;
}
if (session_name.find ('/') != Glib::ustring::npos) {
MessageDialog msg (*_startup, _("To ensure compatibility with various systems\n"
"session names may not contain a '/' character"));
msg.run ();
ARDOUR_COMMAND_LINE::session_name = ""; // cancel that
continue;
}
if (session_name.find ('\\') != Glib::ustring::npos) {
MessageDialog msg (*_startup, _("To ensure compatibility with various systems\n"
"session names may not contain a '\\' character"));
msg.run ();
ARDOUR_COMMAND_LINE::session_name = ""; // cancel that
continue;
}
_session_is_new = true;
}
@@ -2556,7 +2593,9 @@ ARDOUR_UI::close_session()
return;
}
unload_session (true);
if (unload_session (true)) {
return;
}
ARDOUR_COMMAND_LINE::session_name = "";
get_session_parameters (true, false);
@@ -2726,6 +2765,16 @@ ARDOUR_UI::show ()
}
}
void
ARDOUR_UI::launch_chat ()
{
#ifdef __APPLE__
open_uri("http://webchat.freenode.net/?channels=ardour-osx");
#else
open_uri("http://webchat.freenode.net/?channels=ardour");
#endif
}
void
ARDOUR_UI::show_about ()
{
@@ -2734,6 +2783,7 @@ ARDOUR_UI::show_about ()
about->signal_response().connect(sigc::mem_fun (*this, &ARDOUR_UI::about_signal_response) );
}
about->set_transient_for(*editor);
about->show_all ();
}
@@ -2837,9 +2887,6 @@ require some unused files to continue to exist."));
const string dead_sound_directory = _session->session_directory().dead_sound_path().to_string();
/* subst:
%1 - number of files removed
%2 - location of "dead_sounds"
@@ -2848,19 +2895,22 @@ require some unused files to continue to exist."));
*/
const char* bprefix;
double space_adjusted = 0;
if (rep.space < 1048576.0f) {
if (rep.space < 100000.0f) {
bprefix = X_("kilo");
} else if (rep.space < 1048576.0f * 1000) {
} else if (rep.space < 1000000.0f * 1000) {
bprefix = X_("mega");
space_adjusted = truncf((float)rep.space / 1000.0);
} else {
bprefix = X_("giga");
space_adjusted = truncf((float)rep.space / (1000000.0 * 1000));
}
if (removed > 1) {
txt.set_text (string_compose (plural_msg, removed, dead_sound_directory, (float) rep.space / 1024.0f, bprefix));
txt.set_text (string_compose (plural_msg, removed, _session->path() + "dead_sounds", space_adjusted, bprefix));
} else {
txt.set_text (string_compose (singular_msg, removed, dead_sound_directory, (float) rep.space / 1024.0f, bprefix));
txt.set_text (string_compose (singular_msg, removed, _session->path() + "dead_sounds", space_adjusted, bprefix));
}
dhbox.pack_start (*dimage, true, false, 5);

View File

@@ -115,6 +115,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI, public ARDOUR::SessionHandlePtr
void show_splash ();
void hide_splash ();
void launch_chat ();
void show_about ();
void hide_about ();

View File

@@ -218,6 +218,7 @@ ARDOUR_UI::install_actions ()
act = ActionManager::register_toggle_action (common_actions, X_("ToggleBigClock"), _("Big Clock"), sigc::mem_fun(*this, &ARDOUR_UI::toggle_big_clock_window));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::register_action (common_actions, X_("About"), _("About"), sigc::mem_fun(*this, &ARDOUR_UI::show_about));
ActionManager::register_action (common_actions, X_("Chat"), _("Chat"), sigc::mem_fun(*this, &ARDOUR_UI::launch_chat));
ActionManager::register_toggle_action (common_actions, X_("ToggleThemeManager"), _("Theme Manager"), sigc::mem_fun(*this, &ARDOUR_UI::toggle_theme_manager));
ActionManager::register_toggle_action (common_actions, X_("ToggleKeyEditor"), _("Key Bindings"), sigc::mem_fun(*this, &ARDOUR_UI::toggle_key_editor));
ActionManager::register_toggle_action (common_actions, X_("ToggleBundleManager"), _("Bundle Manager"), sigc::mem_fun(*this, &ARDOUR_UI::toggle_bundle_manager));

View File

@@ -473,8 +473,6 @@ AudioRegionView::set_height (gdouble height)
// FIXME: ick
height -= 2;
_height = height;
for (uint32_t n=0; n < wcnt; ++n) {
gdouble ht;
@@ -503,11 +501,6 @@ AudioRegionView::set_height (gdouble height)
manage_zero_line ();
reset_fade_shapes ();
if (name_pixbuf) {
name_pixbuf->raise_to_top();
}
}
void

View File

@@ -497,6 +497,18 @@ CrossfadeEditor::add_control_point (double x, double y)
void
CrossfadeEditor::Point::move_to (double nx, double ny, double xfract, double yfract)
{
if ( xfract < 0.0 ) {
xfract = 0.0;
} else if ( xfract > 1.0 ) {
xfract = 1.0;
}
if ( yfract < 0.0 ) {
yfract = 0.0;
} else if ( yfract > 1.0 ) {
yfract = 1.0;
}
const double half_size = rint(size/2.0);
double x1 = nx - half_size;
double x2 = nx + half_size;

View File

@@ -319,6 +319,7 @@ Editor::Editor ()
have_pending_keyboard_selection = false;
_follow_playhead = true;
_stationary_playhead = false;
_xfade_visibility = true;
editor_ruler_menu = 0;
no_ruler_shown_update = false;
@@ -1730,6 +1731,8 @@ Editor::add_region_context_items (StreamView* sv, boost::shared_ptr<Region> regi
region_mute_item->set_active();
fooc.block (false);
}
items.push_back (MenuElem (_("Transpose"), mem_fun(*this, &Editor::pitch_shift_regions)));
if (!Profile->get_sae()) {
items.push_back (CheckMenuElem (_("Opaque")));
@@ -2243,7 +2246,8 @@ Editor::set_state (const XMLNode& node, int /*version*/)
move (x, y);
if (_session && (prop = node.property ("playhead"))) {
nframes64_t pos = atol (prop->value().c_str());
nframes64_t pos;
sscanf (prop->value().c_str(), "%" PRIi64, &pos);
playhead_cursor->set_position (pos);
} else {
playhead_cursor->set_position (0);
@@ -2341,6 +2345,18 @@ Editor::set_state (const XMLNode& node, int /*version*/)
}
}
if ((prop = node.property ("stationary-playhead"))) {
bool yn = (prop->value() == "yes");
set_stationary_playhead (yn);
RefPtr<Action> act = ActionManager::get_action (X_("Editor"), X_("toggle-stationary-playhead"));
if (act) {
RefPtr<ToggleAction> tact = RefPtr<ToggleAction>::cast_dynamic(act);
if (tact->get_active() != yn) {
tact->set_active (yn);
}
}
}
if ((prop = node.property ("region-list-sort-type"))) {
RegionListSortType st;
_regions->reset_sort_type ((RegionListSortType) string_2_enum (prop->value(), st), true);
@@ -2447,6 +2463,7 @@ Editor::get_state ()
node->add_property ("show-waveforms-recording", _show_waveforms_recording ? "yes" : "no");
node->add_property ("show-measures", _show_measures ? "yes" : "no");
node->add_property ("follow-playhead", _follow_playhead ? "yes" : "no");
node->add_property ("stationary-playhead", _stationary_playhead ? "yes" : "no");
node->add_property ("xfades-visible", _xfade_visibility ? "yes" : "no");
node->add_property ("region-list-sort-type", enum_2_string (_regions->sort_type ()));
node->add_property ("mouse-mode", enum2str(mouse_mode));
@@ -3697,6 +3714,29 @@ Editor::set_follow_playhead (bool yn)
}
}
void
Editor::toggle_stationary_playhead ()
{
RefPtr<Action> act = ActionManager::get_action (X_("Editor"), X_("toggle-stationary-playhead"));
if (act) {
RefPtr<ToggleAction> tact = RefPtr<ToggleAction>::cast_dynamic(act);
set_stationary_playhead (tact->get_active());
}
}
void
Editor::set_stationary_playhead (bool yn)
{
if (_stationary_playhead != yn) {
if ((_stationary_playhead = yn) == true) {
/* catch up */
// FIXME need a 3.0 equivalent of this 2.X call
// update_current_screen ();
}
instant_save ();
}
}
void
Editor::toggle_xfade_active (boost::weak_ptr<Crossfade> wxfade)
{
@@ -4119,10 +4159,11 @@ Editor::undo_visual_state ()
return;
}
redo_visual_stack.push_back (current_visual_state());
VisualState* vs = undo_visual_stack.back();
undo_visual_stack.pop_back();
use_visual_state (*vs);
redo_visual_stack.push_back (vs);
}
void
@@ -4132,10 +4173,11 @@ Editor::redo_visual_state ()
return;
}
undo_visual_stack.push_back (current_visual_state());
VisualState* vs = redo_visual_stack.back();
redo_visual_stack.pop_back();
use_visual_state (*vs);
undo_visual_stack.push_back (vs);
}
void
@@ -4669,6 +4711,8 @@ _idle_resizer (gpointer arg)
void
Editor::add_to_idle_resize (TimeAxisView* view, int32_t h)
{
cerr << "add tav " << view << " with hdelta = " << h << endl;
if (resize_idle_id < 0) {
resize_idle_id = g_idle_add (_idle_resizer, this);
_pending_resize_amount = 0;
@@ -4682,6 +4726,8 @@ Editor::add_to_idle_resize (TimeAxisView* view, int32_t h)
_pending_resize_amount += h;
_pending_resize_view = view;
cerr << "Pending resize amount initially set at " << _pending_resize_amount << endl;
min_resulting = min (min_resulting, int32_t (_pending_resize_view->current_height()) + _pending_resize_amount);
if (selection->tracks.contains (_pending_resize_view)) {
@@ -4697,6 +4743,7 @@ Editor::add_to_idle_resize (TimeAxisView* view, int32_t h)
/* clamp */
if (uint32_t (min_resulting) < TimeAxisView::hSmall) {
_pending_resize_amount += TimeAxisView::hSmall - min_resulting;
cerr << "pending resize amount = " << _pending_resize_amount << endl;
}
}
@@ -4704,6 +4751,9 @@ Editor::add_to_idle_resize (TimeAxisView* view, int32_t h)
bool
Editor::idle_resize ()
{
cerr << "Idle resize, pra = " << _pending_resize_amount
<< " set height to " << _pending_resize_view->current_height() << " + " << _pending_resize_amount << endl;
_pending_resize_view->idle_resize (_pending_resize_view->current_height() + _pending_resize_amount);
if (dynamic_cast<AutomationTimeAxisView*> (_pending_resize_view) == 0 &&
@@ -4716,6 +4766,7 @@ Editor::idle_resize ()
}
}
_pending_resize_amount = 0;
flush_canvas ();
_group_tabs->set_dirty ();
resize_idle_id = -1;
@@ -5121,33 +5172,33 @@ Editor::super_rapid_screen_update ()
playhead_cursor->set_position (frame);
}
#undef CONTINUOUS_SCROLL
#ifndef CONTINUOUS_SCROLL
if (!_stationary_playhead) {
if (!_dragging_playhead && _follow_playhead && _session->requested_return_frame() < 0) {
reset_x_origin_to_follow_playhead ();
}
if (!_dragging_playhead && _follow_playhead && _session->requested_return_frame() < 0) {
reset_x_origin_to_follow_playhead ();
}
#else // CONTINUOUS_SCROLL
/* don't do continuous scroll till the new position is in the rightmost quarter of the
editor canvas
*/
double target = ((double)frame - (double)current_page_frames()/2.0) / frames_per_unit;
if (target <= 0.0) {
target = 0.0;
}
if (fabs(target - current) < current_page_frames() / frames_per_unit) {
target = (target * 0.15) + (current * 0.85);
} else {
/* relax */
}
current = target;
horizontal_adjustment.set_value (current);
#endif // CONTINUOUS_SCROLL
} else {
/* don't do continuous scroll till the new position is in the rightmost quarter of the
editor canvas
*/
#if 0
// FIXME DO SOMETHING THAT WORKS HERE - this is 2.X code
double target = ((double)frame - (double)current_page_frames()/2.0) / frames_per_unit;
if (target <= 0.0) {
target = 0.0;
}
if (fabs(target - current) < current_page_frames() / frames_per_unit) {
target = (target * 0.15) + (current * 0.85);
} else {
/* relax */
}
current = target;
horizontal_adjustment.set_value (current);
#endif
}
}
}

View File

@@ -357,6 +357,10 @@ class Editor : public PublicEditor, public PBD::ScopedConnectionList, public ARD
/* playhead/screen stuff */
void set_stationary_playhead (bool yn);
void toggle_stationary_playhead ();
bool stationary_playhead() const { return _stationary_playhead; }
void set_follow_playhead (bool yn);
void toggle_follow_playhead ();
bool follow_playhead() const { return _follow_playhead; }
@@ -419,6 +423,10 @@ class Editor : public PublicEditor, public PBD::ScopedConnectionList, public ARD
void goto_visual_state (uint32_t);
void save_visual_state (uint32_t);
void queue_draw_resize_line (int at);
void start_resize_line_ops ();
void end_resize_line_ops ();
TrackViewList const & get_track_views () {
return track_views;
}
@@ -1401,6 +1409,8 @@ public:
bool _show_measures;
/// true if the editor should follow the playhead, otherwise false
bool _follow_playhead;
/// true if we scroll the tracks rather than the playhead
bool _stationary_playhead;
/// true if waveforms should be shown while recording audio tracks, otherwise false
bool _show_waveforms_recording;

View File

@@ -207,6 +207,7 @@ Editor::register_actions ()
act = ActionManager::register_action (editor_actions, "track-record-enable-toggle", _("Toggle Record Enable"), sigc::mem_fun(*this, &Editor::toggle_record_enable));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
for (int i = 1; i <= 12; ++i) {
string const a = string_compose (X_("save-visual-state-%1"), i);
@@ -270,17 +271,23 @@ Editor::register_actions ()
act = ActionManager::register_action (editor_actions, "move-selected-tracks-up", _("Move Selected Tracks Up"), sigc::bind (sigc::mem_fun(*_routes, &EditorRoutes::move_selected_tracks), true));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "move-selected-tracks-down", _("Move Selected Tracks Down"), sigc::bind (sigc::mem_fun(*_routes, &EditorRoutes::move_selected_tracks), false));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "scroll-tracks-up", _("Scroll Tracks Up"), sigc::mem_fun(*this, &Editor::scroll_tracks_up));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "scroll-tracks-down", _("Scroll Tracks Down"), sigc::mem_fun(*this, &Editor::scroll_tracks_down));
ActionManager::track_selection_sensitive_actions.push_back (act);
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "step-tracks-up", _("Step Tracks Up"), sigc::mem_fun(*this, &Editor::scroll_tracks_up_line));
ActionManager::track_selection_sensitive_actions.push_back (act);
ActionManager::session_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "step-tracks-down", _("Step Tracks Down"), sigc::mem_fun(*this, &Editor::scroll_tracks_down_line));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "scroll-backward", _("Scroll Backward"), sigc::bind (sigc::mem_fun(*this, &Editor::scroll_backward), 0.8f));
ActionManager::session_sensitive_actions.push_back (act);
@@ -550,6 +557,8 @@ Editor::register_actions ()
act = ActionManager::register_action (editor_actions, "remove-last-capture", _("Remove Last Capture"), (sigc::mem_fun(*this, &Editor::remove_last_capture)));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::register_toggle_action (editor_actions, "toggle-stationary-playhead", _("Stationary Playhead"), (mem_fun(*this, &Editor::toggle_stationary_playhead)));
act = ActionManager::register_action (editor_actions, "insert-time", _("Insert Time"), (sigc::mem_fun(*this, &Editor::do_insert_time)));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
@@ -567,6 +576,7 @@ Editor::register_actions ()
act = ActionManager::register_action (editor_actions, "fit-tracks", _("Fit Selected Tracks"), sigc::mem_fun(*this, &Editor::fit_selected_tracks));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::track_selection_sensitive_actions.push_back (act);
act = ActionManager::register_action (editor_actions, "track-height-largest", _("Largest"), sigc::bind (
sigc::mem_fun(*this, &Editor::set_track_height), TimeAxisView::hLargest));
ActionManager::session_sensitive_actions.push_back (act);

View File

@@ -801,7 +801,7 @@ Editor::scroll_canvas_horizontally ()
}
#ifndef GTKOSX
if (!autoscroll_active) {
if (!autoscroll_active && !_stationary_playhead) {
/* force rulers and canvas to move in lock step */
while (gtk_events_pending ()) {
gtk_main_iteration ();

View File

@@ -1555,7 +1555,7 @@ Editor::temporal_zoom (gdouble fpu)
/* XXX this limit is also in ::set_frames_per_unit() */
if (frames_per_unit <= 2.0 && fpu <= frames_per_unit) {
if (frames_per_unit <= 1.0 && fpu <= frames_per_unit) {
return;
}
@@ -2512,8 +2512,8 @@ Editor::rename_region()
d.get_vbox()->set_border_width (12);
d.get_vbox()->pack_start (hbox, false, false);
d.add_button(Gtk::Stock::OK, Gtk::RESPONSE_OK);
d.add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
d.add_button(Gtk::Stock::OK, Gtk::RESPONSE_OK);
d.set_size_request (300, -1);
d.set_position (Gtk::WIN_POS_MOUSE);

View File

@@ -1255,24 +1255,34 @@ EngineControl::set_state (const XMLNode& root)
} else if (child->name() == "periodsize") {
period_size_combo.set_active_text(strval);
} else if (child->name() == "serverpath") {
/* do not allow us to use a server path that doesn't
exist on this system. this handles cases where
the user has an RC file listing a serverpath
from some other machine.
*/
vector<string>::iterator x;
for (x = server_strings.begin(); x != server_strings.end(); ++x) {
if (*x == strval) {
break;
}
}
if (x != server_strings.end()) {
serverpath_combo.set_active_text (strval);
} else {
warning << string_compose (_("configuration files contain a JACK server path that doesn't exist (%1)"),
strval)
<< endmsg;
}
/* only attempt to set this if we have bothered to look
up server names already. otherwise this is all
redundant (actually, all of this dialog/widget
is redundant in that case ...)
*/
if (!server_strings.empty()) {
/* do not allow us to use a server path that doesn't
exist on this system. this handles cases where
the user has an RC file listing a serverpath
from some other machine.
*/
vector<string>::iterator x;
for (x = server_strings.begin(); x != server_strings.end(); ++x) {
if (*x == strval) {
break;
}
}
if (x != server_strings.end()) {
serverpath_combo.set_active_text (strval);
} else {
warning << string_compose (_("configuration files contain a JACK server path that doesn't exist (%1)"),
strval)
<< endmsg;
}
}
} else if (child->name() == "driver") {
driver_combo.set_active_text(strval);
} else if (child->name() == "interface") {

View File

@@ -322,7 +322,7 @@ GenericPluginUI::ControlUI::ControlUI ()
below). be sure to include a descender.
*/
set_size_request_to_display_given_text (*automate_button.get_child(), _("Mgnual"), 5, 5);
set_size_request_to_display_given_text (automate_button, _("Mgnual"), 15, 10);
ignore_change = 0;
display = 0;

View File

@@ -29,6 +29,7 @@
#include "ardour/track.h"
#include "ardour/audio_track.h"
#include "ardour/midi_track.h"
#include "ardour/mtdm.h"
#include "ardour/data_type.h"
#include "ardour/port.h"
#include "ardour/bundle.h"
@@ -216,16 +217,88 @@ IOSelectorWindow::io_name_changed (void* src)
}
PortInsertUI::PortInsertUI (Gtk::Window* parent, ARDOUR::Session* sess, boost::shared_ptr<ARDOUR::PortInsert> pi)
: input_selector (parent, sess, pi->input())
, output_selector (parent, sess, pi->output())
: _pi (pi)
, latency_button (_("Measure Latency"))
, input_selector (parent, sess, pi->input())
, output_selector (parent, sess, pi->output())
{
latency_hbox.pack_start (latency_button, false, false);
latency_hbox.pack_start (latency_display, false, false);
latency_frame.add (latency_hbox);
output_selector.set_min_height_divisor (2);
input_selector.set_min_height_divisor (2);
pack_start (latency_frame);
pack_start (output_selector, true, true);
pack_start (input_selector, true, true);
latency_button.signal_toggled().connect (mem_fun (*this, &PortInsertUI::latency_button_toggled));
}
bool
PortInsertUI::check_latency_measurement ()
{
MTDM* mtdm = _pi->mtdm ();
if (mtdm->resolve () < 0) {
latency_display.set_text (_("No signal detected"));
return true;
}
if (mtdm->err () > 0.3) {
mtdm->invert ();
mtdm->resolve ();
}
char buf[64];
nframes_t sample_rate = AudioEngine::instance()->frame_rate();
if (sample_rate == 0) {
latency_display.set_text (_("Disconnected from audio engine"));
_pi->stop_latency_detection ();
return false;
}
snprintf (buf, sizeof (buf), "%10.3lf frames %10.3lf ms", mtdm->del (), mtdm->del () * 1000.0f/sample_rate);
bool solid = true;
if (mtdm->err () > 0.2) {
strcat (buf, " ??");
solid = false;
}
if (mtdm->inv ()) {
strcat (buf, " (Inv)");
solid = false;
}
if (solid) {
_pi->set_measured_latency ((nframes_t) rint (mtdm->del()));
strcat (buf, " (set)");
}
latency_display.set_text (buf);
return true;
}
void
PortInsertUI::latency_button_toggled ()
{
if (latency_button.get_active ()) {
_pi->start_latency_detection ();
latency_display.set_text (_("Detecting ..."));
latency_timeout = Glib::signal_timeout().connect (mem_fun (*this, &PortInsertUI::check_latency_measurement), 250);
} else {
_pi->stop_latency_detection ();
latency_timeout.disconnect ();
}
}
void
PortInsertUI::redisplay ()
{

View File

@@ -98,8 +98,18 @@ class PortInsertUI : public Gtk::HBox
void finished (IOSelector::Result);
private:
boost::shared_ptr<ARDOUR::PortInsert> _pi;
Gtk::ToggleButton latency_button;
IOSelector input_selector;
IOSelector output_selector;
Gtk::Label latency_display;
Gtk::Frame latency_frame;
Gtk::HBox latency_hbox;
sigc::connection latency_timeout;
bool check_latency_measurement ();
void latency_button_toggled ();
};
class PortInsertWindow : public ArdourDialog

View File

@@ -281,10 +281,52 @@ fixup_bundle_environment ()
#endif
static void
sigpipe_handler (int /*sig*/)
static gboolean
tell_about_jack_death (void* /* ignored */)
{
cerr << _("SIGPIPE received - JACK has probably died") << endl;
if (AudioEngine::instance()->processed_frames() == 0) {
/* died during startup */
MessageDialog msg (_("JACK exited"), false, Gtk::MESSAGE_INFO, Gtk::BUTTONS_OK);
msg.set_position (Gtk::WIN_POS_CENTER);
msg.set_secondary_text (_(
"JACK exited unexpectedly, and without notifying Ardour.\n\
\n\
This could be due to misconfiguration or to an error inside JACK.\n\
\n\
Click OK to exit Ardour."));
msg.run ();
_exit (0);
} else {
/* engine has already run, so this is a mid-session JACK death */
MessageDialog* msg = manage (new MessageDialog (_("JACK exited"), false, Gtk::MESSAGE_INFO, Gtk::BUTTONS_NONE));
msg->set_secondary_text (_(
"JACK exited unexpectedly, and without notifying Ardour.\n\
\n\
This is probably due to an error inside JACK. You should restart JACK\n\
and reconnect Ardour to it, or exit Ardour now. You cannot save your\n\
session at this time, because we would lose your connection information.\n"));
msg->present ();
}
return false; /* do not call again */
}
static void
sigpipe_handler (int sig)
{
/* XXX fix this so that we do this again after a reconnect to JACK
*/
static bool done_the_jack_thing = false;
if (!done_the_jack_thing) {
AudioEngine::instance()->died ();
g_idle_add (tell_about_jack_death, 0);
done_the_jack_thing = true;
}
}
#ifdef HAVE_LV2

View File

@@ -255,20 +255,17 @@ Marker::Marker (PublicEditor& ed, ArdourCanvas::Group& parent, guint32 rgba, con
/* setup name pixbuf sizes */
name_font = get_font_for_style (N_("MarkerText"));
Gtk::Window win;
Gtk::Label foo;
win.add (foo);
Glib::RefPtr<Pango::Layout> 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_height = height + 6;
Gtkmm2ext::get_ink_pixel_size (layout, width, name_height);
name_pixbuf = new ArdourCanvas::Pixbuf(*group);
name_pixbuf->property_x() = label_offset;
name_pixbuf->property_y() = (13/2) - (name_height/2);
set_name (annotation.c_str());

View File

@@ -207,6 +207,7 @@ MixerStrip::init ()
ARDOUR_UI::instance()->set_tip (&group_button, _("Mix group"), "");
group_button.add (group_label);
group_button.set_name ("MixerGroupButton");
Gtkmm2ext::set_size_request_to_display_given_text (group_button, "Group", 2, 2);
group_label.set_name ("MixerGroupButtonLabel");
comment_button.set_name ("MixerCommentButton");
@@ -1319,12 +1320,7 @@ MixerStrip::route_group_changed ()
RouteGroup *rg = _route->route_group();
if (rg) {
/* XXX: this needs a better algorithm */
string truncated = rg->name ();
if (truncated.length () > 5) {
truncated = truncated.substr (0, 5);
}
group_label.set_text (truncated);
group_label.set_text (PBD::short_version (rg->name(), 5));
} else {
switch (_width) {
case Wide:

View File

@@ -5,6 +5,8 @@
#include <fstream>
#include <gtkmm/stock.h>
#include "pbd/openuri.h"
#include "ardour/ardour.h"
#include "ardour/filesystem_paths.h"
@@ -176,35 +178,16 @@ NagScreen::offer_to_donate ()
/* we don't care if it fails */
open_uri (uri);
PBD::open_uri (uri);
}
void
NagScreen::offer_to_subscribe ()
{
const char* uri = "http://ardour.org/subscribe";
if (open_uri (uri)) {
if (PBD::open_uri (uri)) {
mark_subscriber ();
}
}
bool
NagScreen::open_uri (const char* uri)
{
#ifdef HAVE_GTK_OPEN_URI
GError* err;
return gtk_open_uri (0, uri, GDK_CURRENT_TIME, &err);
#else
#ifdef GTKOSX
extern bool cocoa_open_url (const char*);
return cocoa_open_url (uri);
#else
std::string command = "xdg-open ";
command += uri;
spawn_command_line_async (command);
return true;
#endif
#endif
}

View File

@@ -32,7 +32,6 @@ class NagScreen : public ArdourDialog
void mark_affirmed_subscriber ();
void offer_to_donate ();
void offer_to_subscribe ();
bool open_uri (const char*);
static bool is_subscribed (bool& really);
};

View File

@@ -88,6 +88,7 @@ using namespace Gtkmm2ext;
ProcessorBox* ProcessorBox::_current_processor_box = 0;
RefPtr<Action> ProcessorBox::paste_action;
RefPtr<Action> ProcessorBox::cut_action;
Glib::RefPtr<Gdk::Pixbuf> SendProcessorEntry::_slider;
ProcessorEntry::ProcessorEntry (boost::shared_ptr<Processor> p, Width w)
@@ -494,6 +495,7 @@ ProcessorBox::show_processor_menu (gint arg)
}
}
cut_action->set_sensitive (can_cut());
paste_action->set_sensitive (!_rr_selection.processors.empty());
processor_menu->popup (1, arg);
@@ -1054,6 +1056,27 @@ ProcessorBox::rename_processors ()
}
}
bool
ProcessorBox::can_cut () const
{
vector<boost::shared_ptr<Processor> > sel;
get_selected_processors (sel);
/* cut_processors () does not cut inserts */
for (vector<boost::shared_ptr<Processor> >::const_iterator i = sel.begin (); i != sel.end (); ++i) {
if (boost::dynamic_pointer_cast<PluginInsert>((*i)) != 0 ||
(boost::dynamic_pointer_cast<Send>((*i)) != 0) ||
(boost::dynamic_pointer_cast<Return>((*i)) != 0)) {
return true;
}
}
return false;
}
void
ProcessorBox::cut_processors ()
{
@@ -1333,10 +1356,10 @@ ProcessorBox::deactivate_processor (boost::shared_ptr<Processor> r)
}
void
ProcessorBox::get_selected_processors (ProcSelection& processors)
ProcessorBox::get_selected_processors (ProcSelection& processors) const
{
list<ProcessorEntry*> selection = processor_display.selection ();
for (list<ProcessorEntry*>::iterator i = selection.begin(); i != selection.end(); ++i) {
const list<ProcessorEntry*> selection = processor_display.selection ();
for (list<ProcessorEntry*>::const_iterator i = selection.begin(); i != selection.end(); ++i) {
processors.push_back ((*i)->processor ());
}
}
@@ -1551,9 +1574,9 @@ ProcessorBox::register_actions ()
sigc::ptr_fun (ProcessorBox::rb_clear_post));
/* standard editing stuff */
act = ActionManager::register_action (popup_act_grp, X_("cut"), _("Cut"),
sigc::ptr_fun (ProcessorBox::rb_cut));
ActionManager::plugin_selection_sensitive_actions.push_back(act);
cut_action = ActionManager::register_action (popup_act_grp, X_("cut"), _("Cut"),
sigc::ptr_fun (ProcessorBox::rb_cut));
ActionManager::plugin_selection_sensitive_actions.push_back(cut_action);
act = ActionManager::register_action (popup_act_grp, X_("copy"), _("Copy"),
sigc::ptr_fun (ProcessorBox::rb_copy));
ActionManager::plugin_selection_sensitive_actions.push_back(act);

View File

@@ -238,8 +238,11 @@ class ProcessorBox : public Gtk::HBox, public PluginInterestedObject, public ARD
void rename_processors ();
void for_selected_processors (void (ProcessorBox::*pmf)(boost::shared_ptr<ARDOUR::Processor>));
void get_selected_processors (ProcSelection&);
void get_selected_processors (ProcSelection&) const;
bool can_cut() const;
static Glib::RefPtr<Gtk::Action> cut_action;
static Glib::RefPtr<Gtk::Action> paste_action;
void paste_processor_state (const XMLNodeList&, boost::shared_ptr<ARDOUR::Processor>);

View File

@@ -228,6 +228,10 @@ class PublicEditor : public Gtk::Window, public PBD::StatefulDestructible {
virtual void set_selected_mixer_strip (TimeAxisView&) = 0;
virtual void hide_track_in_display (TimeAxisView& tv, bool temporary = false) = 0;
virtual void set_stationary_playhead (bool yn) = 0;
virtual void toggle_stationary_playhead () = 0;
virtual bool stationary_playhead() const = 0;
/** Set whether the editor should follow the playhead.
* @param yn true to follow playhead, otherwise false.
*/

View File

@@ -94,7 +94,6 @@ RegionView::RegionView (const RegionView& other)
current_visible_sync_position = other.current_visible_sync_position;
valid = false;
_pixel_width = other._pixel_width;
_height = other._height;
GhostRegion::CatchDeletion.connect (*this, ui_bind (&RegionView::remove_ghost, this, _1), gui_context());
}
@@ -114,7 +113,6 @@ RegionView::RegionView (const RegionView& other, boost::shared_ptr<Region> other
current_visible_sync_position = other.current_visible_sync_position;
valid = false;
_pixel_width = other._pixel_width;
_height = other._height;
GhostRegion::CatchDeletion.connect (*this, ui_bind (&RegionView::remove_ghost, this, _1), gui_context());
}
@@ -147,7 +145,6 @@ RegionView::init (Gdk::Color const & basic_color, bool wfd)
editor = 0;
valid = true;
in_destructor = false;
_height = 0;
wait_for_data = wfd;
sync_mark = 0;
sync_line = 0;

View File

@@ -135,7 +135,6 @@ class RegionView : public TimeAxisViewItem
bool valid; ///< see StreamView::redisplay_diskstream()
bool _enable_display; ///< see StreamView::redisplay_diskstream()
double _pixel_width;
double _height;
bool in_destructor;
bool wait_for_data;

View File

@@ -1471,6 +1471,12 @@ RouteTimeAxisView::get_child_list()
}
struct PlaylistSorter {
bool operator() (boost::shared_ptr<Playlist> a, boost::shared_ptr<Playlist> b) const {
return a->sort_id() < b->sort_id();
}
};
void
RouteTimeAxisView::build_playlist_menu (Gtk::Menu * menu)
{
@@ -1486,32 +1492,36 @@ RouteTimeAxisView::build_playlist_menu (Gtk::Menu * menu)
delete playlist_menu;
playlist_menu = new Menu;
playlist_menu->set_name ("ArdourContextMenu");
vector<boost::shared_ptr<Playlist> > playlists;
vector<boost::shared_ptr<Playlist> > playlists, playlists_ds;
boost::shared_ptr<Diskstream> ds = get_diskstream();
RadioMenuItem::Group playlist_group;
_session->playlists->get (playlists);
for (vector<boost::shared_ptr<Playlist> >::iterator i = playlists.begin(); i != playlists.end(); ++i) {
if ((*i)->get_orig_diskstream_id() == ds->id()) {
playlist_items.push_back (RadioMenuElem (playlist_group, (*i)->name(), sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::use_playlist),
boost::weak_ptr<Playlist> (*i))));
if (ds->playlist()->id() == (*i)->id()) {
static_cast<RadioMenuItem*>(&playlist_items.back())->set_active();
}
} else if (ds->playlist()->id() == (*i)->id()) {
playlist_items.push_back (RadioMenuElem (playlist_group, (*i)->name(), sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::use_playlist),
boost::weak_ptr<Playlist>(*i))));
static_cast<RadioMenuItem*>(&playlist_items.back())->set_active();
/* find the playlists for this diskstream */
for (vector<boost::shared_ptr<Playlist> >::iterator i = playlists.begin(); i != playlists.end(); ++i) {
if (((*i)->get_orig_diskstream_id() == ds->id()) || (ds->playlist()->id() == (*i)->id())) {
playlists_ds.push_back(*i);
}
}
/* sort the playlists */
PlaylistSorter cmp;
sort(playlists_ds.begin(), playlists_ds.end(), cmp);
/* add the playlists to the menu */
for (vector<boost::shared_ptr<Playlist> >::iterator i = playlists_ds.begin(); i != playlists_ds.end(); ++i) {
playlist_items.push_back (RadioMenuElem (playlist_group, (*i)->name()));
RadioMenuItem *item = static_cast<RadioMenuItem*>(&playlist_items.back());
item->signal_toggled().connect(sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::use_playlist), item, boost::weak_ptr<Playlist> (*i)));
if (ds->playlist()->id() == (*i)->id()) {
item->set_active();
}
}
playlist_items.push_back (SeparatorElem());
playlist_items.push_back (MenuElem (_("Rename"), sigc::mem_fun(*this, &RouteTimeAxisView::rename_current_playlist)));
playlist_items.push_back (SeparatorElem());
@@ -1535,10 +1545,15 @@ RouteTimeAxisView::build_playlist_menu (Gtk::Menu * menu)
}
void
RouteTimeAxisView::use_playlist (boost::weak_ptr<Playlist> wpl)
RouteTimeAxisView::use_playlist (RadioMenuItem *item, boost::weak_ptr<Playlist> wpl)
{
assert (is_track());
// exit if we were triggered by deactivating the old playlist
if (!item->get_active()) {
return;
}
boost::shared_ptr<Playlist> pl (wpl.lock());
if (!pl) {
@@ -1549,8 +1564,8 @@ RouteTimeAxisView::use_playlist (boost::weak_ptr<Playlist> wpl)
if (apl) {
if (get_diskstream()->playlist() == apl) {
// radio button cotnrols mean this function is called for both the
// old and new playlist
// exit when use_playlist is called by the creation of the playlist menu
// or the playlist choice is unchanged
return;
}
get_diskstream()->use_playlist (apl);

View File

@@ -294,7 +294,7 @@ protected:
virtual Gtk::Menu* build_mode_menu() { return 0; }
virtual Gtk::Menu* build_color_mode_menu() { return 0; }
void use_playlist (boost::weak_ptr<ARDOUR::Playlist>);
void use_playlist (Gtk::RadioMenuItem *item, boost::weak_ptr<ARDOUR::Playlist> wpl);
ArdourCanvas::SimpleRect* timestretch_rect;

View File

@@ -262,9 +262,10 @@ RouteUI::mute_press (GdkEventButton* ev)
// Primary-button2 click is the midi binding click
// button2-click is "momentary"
if (Keyboard::modifier_state_equals (ev->state, Keyboard::ModifierMask (Keyboard::PrimaryModifier))) {
return false;
}
if (mute_button->on_button_press_event (ev)) {
return true;
}
_mute_release = new SoloMuteRelease (_route->muted ());
}
@@ -357,9 +358,9 @@ RouteUI::solo_press(GdkEventButton* ev)
// Primary-button2 click is the midi binding click
// button2-click is "momentary"
if (Keyboard::modifier_state_equals (ev->state, Keyboard::ModifierMask (Keyboard::PrimaryModifier))) {
return false;
}
if (solo_button->on_button_press_event (ev)) {
return true;
}
_solo_release = new SoloMuteRelease (_route->soloed());
}
@@ -491,10 +492,10 @@ RouteUI::rec_enable_press(GdkEventButton* ev)
if (!ignore_toggle && is_track() && rec_enable_button) {
if (Keyboard::is_button2_event (ev) && Keyboard::modifier_state_equals (ev->state, Keyboard::PrimaryModifier)) {
if (Keyboard::is_button2_event (ev)) {
// do nothing on midi sigc::bind event
return false;
return rec_enable_button->on_button_press_event (ev);
} else if (Keyboard::modifier_state_equals (ev->state, Keyboard::ModifierMask (Keyboard::PrimaryModifier|Keyboard::TertiaryModifier))) {

View File

@@ -443,6 +443,10 @@ SoundFileBrowser::SoundFileBrowser (Gtk::Window& parent, string title, ARDOUR::S
chooser.set_select_multiple (true);
chooser.signal_update_preview().connect(sigc::mem_fun(*this, &SoundFileBrowser::update_preview));
chooser.signal_file_activated().connect (sigc::mem_fun (*this, &SoundFileBrowser::chooser_file_activated));
#ifdef GTKOSX
/* some broken redraw behaviour - this is a bandaid */
chooser.signal_selection_changed().connect (mem_fun (chooser, &Widget::queue_draw));
#endif
if (!persistent_folder.empty()) {
chooser.set_current_folder (persistent_folder);
@@ -1000,7 +1004,7 @@ SoundFileOmega::reset_options ()
channel_strings.push_back (_("sequence files"));
}
if (same_size) {
channel_strings.push_back (_("all files in one region"));
channel_strings.push_back (_("all files in one track"));
}
}

View File

@@ -153,6 +153,7 @@ TimeAxisView::TimeAxisView (ARDOUR::Session* sess, PublicEditor& ed, TimeAxisVie
resizer.signal_button_press_event().connect (sigc::mem_fun (*this, &TimeAxisView::resizer_button_press));
resizer.signal_button_release_event().connect (sigc::mem_fun (*this, &TimeAxisView::resizer_button_release));
resizer.signal_motion_notify_event().connect (sigc::mem_fun (*this, &TimeAxisView::resizer_motion));
resizer.set_events (Gdk::BUTTON_PRESS_MASK|
Gdk::BUTTON_RELEASE_MASK|
Gdk::POINTER_MOTION_MASK|
@@ -1307,13 +1308,11 @@ TimeAxisView::idle_resize (uint32_t h)
bool
TimeAxisView::resizer_motion (GdkEventMotion* ev)
{
if (_resize_drag_start < 0) {
return true;
}
int32_t const delta = (int32_t) floor (ev->y_root - _resize_drag_start);
_editor.add_to_idle_resize (this, delta);
_resize_drag_start = ev->y_root;
if (_resize_drag_start >= 0) {
int32_t const delta = (int32_t) floor (ev->y_root - _resize_drag_start);
_editor.add_to_idle_resize (this, delta);
_resize_drag_start = ev->y_root;
}
return true;
}

View File

@@ -78,7 +78,7 @@ double TimeAxisViewItem::NAME_HIGHLIGHT_THRESH;
TimeAxisViewItem::TimeAxisViewItem(const string & it_name, ArdourCanvas::Group& parent, TimeAxisView& tv, double spu, Gdk::Color const & base_color,
nframes64_t start, nframes64_t duration, bool recording,
Visibility vis)
: trackview (tv), _recregion(recording)
: trackview (tv), _height (1.0), _recregion(recording)
{
if (!have_name_font) {
@@ -558,6 +558,8 @@ TimeAxisViewItem::set_name_text(const ustring& new_name)
void
TimeAxisViewItem::set_height (double height)
{
_height = height;
if (name_highlight) {
if (height < NAME_HIGHLIGHT_THRESH) {
name_highlight->hide ();
@@ -841,9 +843,7 @@ TimeAxisViewItem::reset_width_dependent_items (double pixel_width)
if (name_highlight) {
double height = name_highlight->property_y2 ();
if (height < NAME_HIGHLIGHT_THRESH) {
if (_height < NAME_HIGHLIGHT_THRESH) {
name_highlight->hide();
high_enough_for_name = false;
} else {
@@ -853,7 +853,7 @@ TimeAxisViewItem::reset_width_dependent_items (double pixel_width)
}
high_enough_for_name = true;
}
if (visibility & FullWidthNameHighlight) {
name_highlight->property_x2() = pixel_width;
} else {
@@ -878,6 +878,8 @@ TimeAxisViewItem::reset_width_dependent_items (double pixel_width)
frame_handle_end->property_x2() = pixel_width;
}
}
update_name_pixbuf_visibility ();
}
void

View File

@@ -467,6 +467,7 @@ class TimeAxisViewItem : public Selectable, public PBD::ScopedConnectionList
ArdourCanvas::SimpleRect* frame_handle_start;
ArdourCanvas::SimpleRect* frame_handle_end;
double _height;
Visibility visibility;
bool _recregion;

View File

@@ -247,7 +247,6 @@ _ the regular process() call to session->process() is not made.
nframes_t _processed_frames;
bool _freewheeling;
bool _freewheel_pending;
bool _freewheel_thread_registered;
boost::function<int(nframes_t)> freewheel_action;
bool reconnect_on_halt;
int _usecs_per_cycle;

View File

@@ -116,6 +116,7 @@ class Playlist : public SessionObject
bool used () const { return _refcnt != 0; }
bool set_name (const std::string& str);
int sort_id() { return _sort_id; }
const DataType& data_type() const { return _type; }
@@ -240,6 +241,7 @@ class Playlist : public SessionObject
std::set<boost::shared_ptr<Region> > all_regions; /* all regions ever added to this playlist */
PBD::ScopedConnectionList region_state_changed_connections;
DataType _type;
int _sort_id;
mutable gint block_notifications;
mutable gint ignore_state_changes;
mutable Glib::RecMutex region_lock;
@@ -289,6 +291,8 @@ class Playlist : public SessionObject
virtual void flush_notifications ();
void clear_pending ();
void _set_sort_id ();
void notify_region_removed (boost::shared_ptr<Region>);
void notify_region_added (boost::shared_ptr<Region>);
void notify_length_changed ();

View File

@@ -29,6 +29,7 @@
#include "ardour/types.h"
class XMLNode;
class MTDM;
namespace ARDOUR {
@@ -64,6 +65,12 @@ class PortInsert : public IOProcessor
uint32_t bit_slot() const { return bitslot; }
void start_latency_detection ();
void stop_latency_detection ();
MTDM* mtdm () const { return _mtdm; }
void set_measured_latency (nframes_t);
private:
/* disallow copy construction */
PortInsert (const PortInsert&);
@@ -71,7 +78,10 @@ class PortInsert : public IOProcessor
boost::shared_ptr<Delivery> _out;
uint32_t bitslot;
};
MTDM* _mtdm;
bool _latency_detect;
nframes_t _latency_flush_frames;
nframes_t _measured_latency;};
} // namespace ARDOUR

View File

@@ -136,7 +136,7 @@ CONFIG_VARIABLE (bool, periodic_safety_backups, "periodic-safety-backups", true)
CONFIG_VARIABLE (uint32_t, periodic_safety_backup_interval, "periodic-safety-backup-interval", 120)
CONFIG_VARIABLE (float, automation_interval, "automation-interval", 50)
CONFIG_VARIABLE (bool, sync_all_route_ordering, "sync-all-route-ordering", true)
CONFIG_VARIABLE (bool, only_copy_imported_files, "only-copy-imported-files", true)
CONFIG_VARIABLE (bool, only_copy_imported_files, "only-copy-imported-files", false)
CONFIG_VARIABLE (bool, new_plugins_active, "new-plugins-active", true)
CONFIG_VARIABLE (std::string, keyboard_layout, "keyboard-layout", "ansi")
CONFIG_VARIABLE (std::string, default_bindings, "default-bindings", "ardour")

View File

@@ -76,7 +76,6 @@ AudioEngine::AudioEngine (string client_name)
_jack = 0;
_frame_rate = 0;
_buffer_size = 0;
_freewheel_thread_registered = false;
_freewheeling = false;
m_meter_thread = 0;
@@ -1104,16 +1103,11 @@ AudioEngine::freewheel (bool onoff)
GET_PRIVATE_JACK_POINTER_RET (_jack, -1);
if (onoff != _freewheeling) {
if (onoff) {
_freewheel_thread_registered = false;
}
return jack_set_freewheel (_priv_jack, onoff);
return jack_set_freewheel (_priv_jack, onoff);
} else {
/* already doing what has been asked for */
return 0;
/* already doing what has been asked for */
return 0;
}
}

View File

@@ -1387,14 +1387,22 @@ AudioRegion::get_transients (AnalysisFeatureList& results, bool force_new)
/* no existing/complete transient info */
static bool analyse_dialog_shown = false; /* global per instance of Ardour */
if (!Config->get_auto_analyse_audio()) {
pl->session().Dialog (_("\
You have requested an operation that requires audio analysis.\n\n\
if (!analyse_dialog_shown) {
pl->session().Dialog (_("\
You have requested an operation that requires audio analysis.\n\n \
You currently have \"auto-analyse-audio\" disabled, which means\n\
that transient data must be generated every time it is required.\n\n\
If you are doing work that will require transient data on a\n\
regular basis, you should probably enable \"auto-analyse-audio\"\n\
then quit ardour and restart."));
+then quit ardour and restart.\n\n\
+This dialog will not display again. But you may notice a slight delay\n\
+in this and future transient-detection operations.\n\
+"));
analyse_dialog_shown = true;
}
}
TransientDetector t (pl->session().frame_rate());

View File

@@ -100,6 +100,7 @@ Crossfade::Crossfade (boost::shared_ptr<AudioRegion> in, boost::shared_ptr<Audio
_out = out;
_anchor_point = ap;
_fixed = true;
_follow_overlap = false;
initialize ();
}

View File

@@ -205,7 +205,7 @@ map_existing_mono_sources (const vector<string>& new_paths, Session& /*sess*/,
static bool
create_mono_sources_for_writing (const vector<string>& new_paths, Session& sess,
uint samplerate, vector<boost::shared_ptr<Source> >& newfiles,
nframes64_t /*timeline_position*/)
framepos_t timeline_position)
{
for (vector<string>::const_iterator i = new_paths.begin(); i != new_paths.end(); ++i)
{
@@ -229,6 +229,14 @@ create_mono_sources_for_writing (const vector<string>& new_paths, Session& sess,
}
newfiles.push_back(boost::dynamic_pointer_cast<Source>(source));
/* for audio files, reset the timeline position so that any BWF-ish
information in the original files we are importing from is maintained.
*/
boost::shared_ptr<AudioFileSource> afs;
afs = boost::dynamic_pointer_cast<AudioFileSource>(source);
afs->set_timeline_position(timeline_position);
}
return true;
}
@@ -425,13 +433,13 @@ Session::import_audiofiles (ImportStatus& status)
get_best_session_directory_for_new_source (),
channels);
Sources newfiles;
nframes64_t natural_position = source ? source->natural_position() : 0;
framepos_t natural_position = source ? source->natural_position() : 0;
if (status.replace_existing_source) {
fatal << "THIS IS NOT IMPLEMENTED YET, IT SHOULD NEVER GET CALLED!!! DYING!" << endmsg;
status.cancel = !map_existing_mono_sources (new_paths, *this, frame_rate(), newfiles, this);
} else {
status.cancel = !create_mono_sources_for_writing (new_paths, *this, frame_rate(), newfiles, natural_position);
status.cancel = !create_mono_sources_for_writing (new_paths, *this, frame_rate(), newfiles, natural_position);
}
// copy on cancel/failure so that any files that were created will be removed below
@@ -468,7 +476,7 @@ Session::import_audiofiles (ImportStatus& status)
for (Sources::iterator x = all_new_sources.begin(); x != all_new_sources.end(); ) {
if ((afs = boost::dynamic_pointer_cast<AudioFileSource>(*x)) != 0) {
afs->update_header(0, *now, xnow);
afs->update_header((*x)->natural_position(), *now, xnow);
afs->done_with_peakfile_writes ();
/* now that there is data there, requeue the file for analysis */

View File

@@ -178,8 +178,6 @@ LadspaPlugin::default_value (uint32_t port)
sr_scaling = true;
}
/* FIXME: add support for logarithmic defaults */
else if (LADSPA_IS_HINT_DEFAULT_LOW(prh[port].HintDescriptor)) {
if (LADSPA_IS_HINT_LOGARITHMIC(prh[port].HintDescriptor)) {
ret = exp(log(prh[port].LowerBound) * 0.75f + log(prh[port].UpperBound) * 0.25f);

View File

@@ -25,6 +25,8 @@
#include <string>
#include <climits>
#include <boost/lexical_cast.hpp>
#include "pbd/failed_constructor.h"
#include "pbd/stateful_diff_command.h"
#include "pbd/xml++.h"
@@ -150,6 +152,7 @@ Playlist::Playlist (Session& sess, string nom, DataType type, bool hide)
init (hide);
first_set_state = false;
_name = nom;
_set_sort_id ();
}
@@ -164,6 +167,7 @@ Playlist::Playlist (Session& sess, const XMLNode& node, DataType type, bool hide
init (hide);
_name = "unnamed"; /* reset by set_state */
_set_sort_id ();
/* set state called by derived class */
}
@@ -359,6 +363,32 @@ Playlist::~Playlist ()
/* GoingAway must be emitted by derived classes */
}
void
Playlist::_set_sort_id ()
{
/*
Playlists are given names like <track name>.<id>
or <track name>.<edit group name>.<id> where id
is an integer. We extract the id and sort by that.
*/
size_t dot_position = _name.val().find_last_of(".");
if (dot_position == string::npos) {
_sort_id = 0;
} else {
string t = _name.val().substr(dot_position + 1);
try {
_sort_id = boost::lexical_cast<int>(t);
}
catch (boost::bad_lexical_cast e) {
_sort_id = 0;
}
}
}
bool
Playlist::set_name (const string& str)
{
@@ -370,9 +400,13 @@ Playlist::set_name (const string& str)
if (_refcnt > 2) {
return false;
} else {
return SessionObject::set_name(str);
}
}
bool ret = SessionObject::set_name(str);
if (ret) {
_set_sort_id ();
}
return ret;
}
/***********************************************************************
@@ -2121,6 +2155,7 @@ Playlist::set_state (const XMLNode& node, int version)
if (prop->name() == X_("name")) {
_name = prop->value();
_set_sort_id ();
} else if (prop->name() == X_("id")) {
_id = prop->value();
} else if (prop->name() == X_("orig_diskstream_id")) {

View File

@@ -23,14 +23,15 @@
#include "pbd/failed_constructor.h"
#include "pbd/xml++.h"
#include "ardour/audioengine.h"
#include "ardour/audio_port.h"
#include "ardour/buffer_set.h"
#include "ardour/delivery.h"
#include "ardour/port_insert.h"
#include "ardour/mtdm.h"
#include "ardour/plugin.h"
#include "ardour/port.h"
#include "ardour/port_insert.h"
#include "ardour/route.h"
#include "ardour/buffer_set.h"
#include "ardour/audioengine.h"
#include "ardour/session.h"
#include "ardour/types.h"
@@ -44,6 +45,11 @@ PortInsert::PortInsert (Session& s, boost::shared_ptr<MuteMaster> mm)
: IOProcessor (s, true, true, string_compose (_("insert %1"), (bitslot = s.next_insert_id()) + 1), "")
, _out (new Delivery (s, _output, mm, _name, Delivery::Insert))
{
_mtdm = 0;
_latency_detect = false;
_latency_flush_frames = false;
_measured_latency = 0;
ProcessorCreated (this); /* EMIT SIGNAL */
}
@@ -52,6 +58,11 @@ PortInsert::PortInsert (Session& s, boost::shared_ptr<MuteMaster> mm, const XMLN
, _out (new Delivery (s, _output, mm, _name, Delivery::Insert))
{
_mtdm = 0;
_latency_detect = false;
_latency_flush_frames = false;
_measured_latency = 0;
if (set_state (node, Stateful::loading_state_version)) {
throw failed_constructor();
}
@@ -61,6 +72,33 @@ PortInsert::PortInsert (Session& s, boost::shared_ptr<MuteMaster> mm, const XMLN
PortInsert::~PortInsert ()
{
delete _mtdm;
}
void
PortInsert::start_latency_detection ()
{
if (_mtdm != 0) {
delete _mtdm;
}
_mtdm = new MTDM;
_latency_flush_frames = false;
_latency_detect = true;
_measured_latency = 0;
}
void
PortInsert::stop_latency_detection ()
{
_latency_flush_frames = signal_latency() + _session.engine().frames_per_cycle();
_latency_detect = false;
}
void
PortInsert::set_measured_latency (nframes_t n)
{
_measured_latency = n;
}
void
@@ -70,6 +108,38 @@ PortInsert::run (BufferSet& bufs, sframes_t start_frame, sframes_t end_frame, nf
return;
}
if (_latency_detect) {
if (_input->n_ports().n_audio() != 0) {
AudioBuffer& outbuf (_output->ports().nth_audio_port(0)->get_audio_buffer (nframes));
Sample* in = _input->ports().nth_audio_port(0)->get_audio_buffer (nframes).data();
Sample* out = outbuf.data();
_mtdm->process (nframes, in, out);
outbuf.is_silent (false);
}
return;
} else if (_latency_flush_frames) {
/* wait for the entire input buffer to drain before picking up input again so that we can't
hear the remnants of whatever MTDM pumped into the pipeline.
*/
silence (nframes);
if (_latency_flush_frames > nframes) {
_latency_flush_frames -= nframes;
} else {
_latency_flush_frames = 0;
}
return;
}
if (!_active && !_pending_active) {
/* deliver silence */
silence (nframes);
@@ -151,7 +221,11 @@ PortInsert::signal_latency() const
need to take that into account too.
*/
return _session.engine().frames_per_cycle() + _input->signal_latency();
if (_measured_latency == 0) {
return _session.engine().frames_per_cycle() + _input->signal_latency();
} else {
return _measured_latency;
}
}
bool

View File

@@ -16,6 +16,8 @@
675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <glibmm/ustring.h>
#include "ardour/port_set.h"
#include "ardour/midi_port.h"
#include "ardour/audio_port.h"
@@ -30,7 +32,41 @@ PortSet::PortSet()
static bool sort_ports_by_name (Port* a, Port* b)
{
return (a->name() < b->name());
Glib::ustring aname (a->name());
Glib::ustring bname (b->name());
Glib::ustring::size_type last_digit_position_a = aname.size();
Glib::ustring::const_reverse_iterator r_iterator = aname.rbegin();
while (r_iterator!= aname.rend() && Glib::Unicode::isdigit(*r_iterator)) {
r_iterator++;
last_digit_position_a--;
}
Glib::ustring::size_type last_digit_position_b = bname.size();
r_iterator = bname.rbegin();
while (r_iterator != bname.rend() && Glib::Unicode::isdigit(*r_iterator)) {
r_iterator++;
last_digit_position_b--;
}
// if some of the names don't have a number as posfix, compare as strings
if (last_digit_position_a == aname.size() or last_digit_position_b == bname.size()) {
return aname < bname;
}
const std::string prefix_a = aname.substr(0, last_digit_position_a - 1);
const unsigned int posfix_a = std::atoi(aname.substr(last_digit_position_a, aname.size() - last_digit_position_a).c_str());
const std::string prefix_b = bname.substr(0, last_digit_position_b - 1);
const unsigned int posfix_b = std::atoi(bname.substr(last_digit_position_b, bname.size() - last_digit_position_b).c_str());
if (prefix_a != prefix_b) {
return aname < bname;
} else {
return posfix_a < posfix_b;
}
}
void

View File

@@ -32,6 +32,7 @@ gtkmm2ext_sources = [
'focus_entry.cc',
'grouped_buttons.cc',
'gtk_ui.cc',
'gtkapplication.c',
'idle_adjustment.cc',
'keyboard.cc',
'motionfeedback.cc',
@@ -84,7 +85,9 @@ def build(bld):
'-DLOCALEDIR="' + os.path.join(
os.path.normpath(bld.env['DATADIRNAME']), 'locale') + '"']
if bld.env['GTKOSX']:
obj.source += ['sync-menu.c']
obj.source += ['gtkapplication_quartz.mm']
else:
obj.source += ['gtkapplication_x11.c']
def shutdown():
autowaf.shutdown()

28
libs/pbd/openuri.cc Normal file
View File

@@ -0,0 +1,28 @@
#ifdef WAF_BUILD
#include "libpbd-config.h"
#endif
#include <string>
#include <glibmm/spawn.h>
#include "pbd/openuri.h"
bool
PBD::open_uri (const char* uri)
{
#ifdef HAVE_GTK_OPEN_URI
GError* err;
return gtk_open_uri (0, uri, GDK_CURRENT_TIME, &err);
#else
#ifdef __APPLE__
extern bool cocoa_open_url (const char*);
return cocoa_open_url (uri);
#else
std::string command = "xdg-open ";
command += uri;
Glib::spawn_command_line_async (command);
return true;
#endif
#endif
}

8
libs/pbd/pbd/openuri.h Normal file
View File

@@ -0,0 +1,8 @@
#ifndef __libpbd_openuri_h__
#define __libpbd_openuri_h__
namespace PBD {
bool open_uri (const char*);
}
#endif

View File

@@ -73,6 +73,7 @@ def build(bld):
locale_guard.cc
malign.cc
mountpoint.cc
openuri.cc
pathscanner.cc
pool.cc
property_list.cc

View File

@@ -321,6 +321,7 @@ OSC::register_callbacks()
REGISTER_CALLBACK (serv, "/ardour/transport_stop", "", transport_stop);
REGISTER_CALLBACK (serv, "/ardour/transport_play", "", transport_play);
REGISTER_CALLBACK (serv, "/ardour/set_transport_speed", "f", set_transport_speed);
REGISTER_CALLBACK (serv, "/ardour/locate", "ii", locate);
REGISTER_CALLBACK (serv, "/ardour/save_state", "", save_state);
REGISTER_CALLBACK (serv, "/ardour/prev_marker", "", prev_marker);
REGISTER_CALLBACK (serv, "/ardour/next_marker", "", next_marker);

View File

@@ -167,6 +167,7 @@ class OSC : public ARDOUR::ControlProtocol, public AbstractUI<OSCUIRequest>
return 0; \
}
PATH_CALLBACK2(locate,i,i);
PATH_CALLBACK2(route_mute,i,i);
PATH_CALLBACK2(route_solo,i,i);
PATH_CALLBACK2(route_recenable,i,i);

View File

@@ -78,11 +78,11 @@ foreach my $tmp (keys %sources) {
"-t", "raw", # /dev/zero is raw :)
"-r", $samplerate, # set sample rate
"-c", "1", # 1 channel
"-b", # input in bytes
"-b", "8" # input in 8 bit chunks
"-s", # signed
"/dev/zero", # input signal
"-w", # output 16 bit
"-b", "16" # input in 16 bit chunks
"-t", "wav", # format wav
$audioFileDirectory."/".$sources{$tmp}->{name}, # filename
"trim", "0", $sources{$tmp}->{calculated_length}."s" # trim silence to wanted sample amount