mirror of
https://github.com/cookiengineer/audacity
synced 2025-05-01 08:09:41 +02:00
Merge branch 'master' into refactor
This commit is contained in:
commit
210b3b751c
@ -62,10 +62,12 @@ nobase_dist_pkgdata_DATA = \
|
||||
plug-ins/beat.ny \
|
||||
plug-ins/clicktrack.ny \
|
||||
plug-ins/clipfix.ny \
|
||||
plug-ins/crossfadeclips.ny \
|
||||
plug-ins/crossfadetracks.ny \
|
||||
plug-ins/delay.ny \
|
||||
plug-ins/equalabel.ny \
|
||||
plug-ins/highpass.ny \
|
||||
plug-ins/limiter.ny \
|
||||
plug-ins/lowpass.ny \
|
||||
plug-ins/notch.ny \
|
||||
plug-ins/pluck.ny \
|
||||
|
@ -534,10 +534,12 @@ nobase_dist_pkgdata_DATA = \
|
||||
plug-ins/beat.ny \
|
||||
plug-ins/clicktrack.ny \
|
||||
plug-ins/clipfix.ny \
|
||||
plug-ins/crossfadeclips.ny \
|
||||
plug-ins/crossfadetracks.ny \
|
||||
plug-ins/delay.ny \
|
||||
plug-ins/equalabel.ny \
|
||||
plug-ins/highpass.ny \
|
||||
plug-ins/limiter.ny \
|
||||
plug-ins/lowpass.ny \
|
||||
plug-ins/notch.ny \
|
||||
plug-ins/pluck.ny \
|
||||
|
@ -44,6 +44,7 @@
|
||||
|
||||
#include <wx/cmdline.h>
|
||||
#include <wx/fileconf.h>
|
||||
#include <wx/intl.h>
|
||||
|
||||
class EffectAutomationParameters : public wxFileConfig
|
||||
{
|
||||
@ -82,6 +83,22 @@ public:
|
||||
return wxFileConfig::DoReadLong(NormalizeName(key), pl);
|
||||
}
|
||||
|
||||
virtual bool DoReadDouble(const wxString & key, double *pd) const
|
||||
{
|
||||
wxString str;
|
||||
if (Read(key, &str))
|
||||
{
|
||||
wxString dec = wxLocale::GetInfo(wxLOCALE_DECIMAL_POINT, wxLOCALE_CAT_NUMBER);
|
||||
|
||||
str.Replace(wxT(","), dec);
|
||||
str.Replace(wxT("."), dec);
|
||||
|
||||
return str.ToDouble(pd);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
virtual bool DoWriteString(const wxString & key, const wxString & szValue)
|
||||
{
|
||||
return wxFileConfig::DoWriteString(NormalizeName(key), szValue);
|
||||
@ -94,7 +111,7 @@ public:
|
||||
|
||||
virtual bool DoWriteDouble(const wxString & key, double value)
|
||||
{
|
||||
return DoWriteString(key, wxString::Format(wxT("%.12g"), value));
|
||||
return DoWriteString(key, wxString::Format(wxT("%.12f"), value));
|
||||
}
|
||||
|
||||
bool ReadFloat(const wxString & key, float *pf) const
|
||||
@ -209,19 +226,6 @@ public:
|
||||
return (*val != wxNOT_FOUND);
|
||||
}
|
||||
|
||||
wxString NormalizeName(const wxString & name) const
|
||||
{
|
||||
wxString cleaned = name;
|
||||
|
||||
cleaned.Trim(true).Trim(false);
|
||||
cleaned.Replace(wxT(" "), wxT("_"));
|
||||
cleaned.Replace(wxT("/"), wxT("_"));
|
||||
cleaned.Replace(wxT("\\"), wxT("_"));
|
||||
cleaned.Replace(wxT(":"), wxT("_"));
|
||||
|
||||
return cleaned;
|
||||
}
|
||||
|
||||
bool GetParameters(wxString & parms)
|
||||
{
|
||||
wxFileConfig::SetPath(wxT("/"));
|
||||
@ -270,6 +274,19 @@ public:
|
||||
return true;
|
||||
}
|
||||
|
||||
wxString NormalizeName(const wxString & name) const
|
||||
{
|
||||
wxString cleaned = name;
|
||||
|
||||
cleaned.Trim(true).Trim(false);
|
||||
cleaned.Replace(wxT(" "), wxT("_"));
|
||||
cleaned.Replace(wxT("/"), wxT("_"));
|
||||
cleaned.Replace(wxT("\\"), wxT("_"));
|
||||
cleaned.Replace(wxT(":"), wxT("_"));
|
||||
|
||||
return cleaned;
|
||||
}
|
||||
|
||||
wxString Escape(wxString val)
|
||||
{
|
||||
val.Replace(wxT("\\"), wxT("\\\\"), true);
|
||||
|
130
plug-ins/crossfadeclips.ny
Normal file
130
plug-ins/crossfadeclips.ny
Normal file
@ -0,0 +1,130 @@
|
||||
;nyquist plugin
|
||||
;version 4
|
||||
;type process
|
||||
;mergeclips 1
|
||||
;restoresplits 0
|
||||
;name "Crossfade Clips"
|
||||
;action "Crossfading..."
|
||||
;author "Steve Daulton"
|
||||
;copyright "Released under terms of the GNU General Public License version 2"
|
||||
|
||||
|
||||
;; crossfadeclips.ny by Steve Daulton Dec 2014.
|
||||
;; Released under terms of the GNU General Public License version 2:
|
||||
;; http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
|
||||
|
||||
;; Instructions:
|
||||
;; Place two audio clips into the same track.
|
||||
;; Select (approximately) the same amount of audio from the
|
||||
;; end of one clip and the start of the other.
|
||||
;; Apply the effect.
|
||||
;; The selected regions will be crossfaded.
|
||||
;;
|
||||
;; Note, the audio clips do not need to be touching. Any
|
||||
;; white-space between the clips is ignored.
|
||||
;;
|
||||
;; If the selected region is continuous audio (no splits),
|
||||
;; the the first and last halves of the selected audio
|
||||
;; will be crossfaded.
|
||||
;;
|
||||
;; Advanced Tip:
|
||||
;; A discontinuity in a waveform may be smoothed by applying
|
||||
;; a short crossfade across the glitch.
|
||||
|
||||
;; Limitations (should not occur in normal usage).
|
||||
;; 1) There may be no more than two clips selected in each channel.
|
||||
;; 2) The selection may not start or end in white-space.
|
||||
|
||||
|
||||
(setf err1 "Error.\nInvalid selection.\nMore than 2 audio clips selected.")
|
||||
(setf err2 "Error.\nInvalid selection.\nEmpty space at start/ end of the selection.")
|
||||
|
||||
|
||||
(defun find-ends (T0 T1 clips)
|
||||
"Look for a split or gap within the selection, or return the mid-point"
|
||||
(let ((trk-ends ()) ;starts of clips
|
||||
(trk-starts ())) ;ends of clips
|
||||
(dolist (clip clips)
|
||||
;; look for clip enclosing the selection.
|
||||
(when (and (>= (second clip) T1) (<= (first clip) T0))
|
||||
(psetq trk-ends (list (/ (+ T0 T1) 2))
|
||||
trk-starts (list (/ (+ T0 T1) 2)))
|
||||
(return))
|
||||
;; look for track starts.
|
||||
(when (and (> (first clip) T0) (< (first clip) T1))
|
||||
(push (first clip) trk-starts))
|
||||
;; look for track ends.
|
||||
(when (and (> (second clip) T0) (< (second clip) T1))
|
||||
(push (second clip) trk-ends))
|
||||
; stop looking when we have passed end of selection.
|
||||
(when (> (first clip) T1) (return)))
|
||||
;; if exactly one split position for crossfading,
|
||||
;; return clip positions, else error.
|
||||
(cond
|
||||
((and (= (length trk-ends) 1)
|
||||
(= (length trk-starts) 1)
|
||||
(<= (car trk-ends) (car trk-starts)))
|
||||
(list (car trk-ends)(car trk-starts)))
|
||||
((or (> (length trk-ends) 1)
|
||||
(> (length trk-starts) 1))
|
||||
(throw 'error err1))
|
||||
(T (throw 'error err2)))))
|
||||
|
||||
(defun crossfade (sig out-end in-start end)
|
||||
"Do the crossfade"
|
||||
(abs-env
|
||||
(control-srate-abs *sound-srate*
|
||||
(let* ((fade-out (mult sig (env out-end 0)))
|
||||
(cflen (max out-end (- end in-start))) ;crossfade length
|
||||
(finstart (max (- out-end (- end in-start)) 0))
|
||||
(fade-in (mult (extract (- end cflen) end sig)
|
||||
(env (- cflen finstart) 1 finstart))))
|
||||
(sim fade-out fade-in)))))
|
||||
|
||||
(defun env (dur direction &optional (offset 0))
|
||||
"Generate envelope for crossfade"
|
||||
(abs-env
|
||||
(if (< dur 0.01) ;make it linear
|
||||
(control-srate-abs *sound-srate*
|
||||
(if (= direction 0)
|
||||
(pwlv 1 dur 0) ;fade out
|
||||
(pwlv 0 offset 0 (+ offset dur) 1))) ;fade in
|
||||
(if (= direction 0) ;cosine curve
|
||||
(cos-curve dur 0)
|
||||
(seq (s-rest offset)
|
||||
(cos-curve dur 1))))))
|
||||
|
||||
(defun cos-curve (dur direction)
|
||||
"Generate cosine curve"
|
||||
(if (= direction 0) ;fade out
|
||||
(osc (hz-to-step (/ 0.25 dur)) dur *sine-table* 90)
|
||||
(osc (hz-to-step (/ 0.25 dur)) dur *sine-table* 0)))
|
||||
|
||||
(defun process (sig t0 t1 clips)
|
||||
"Find the split positions and crossfade"
|
||||
(setf fadeclips
|
||||
(multichan-expand #'find-ends t0 t1 clips))
|
||||
(if (arrayp fadeclips)
|
||||
(prog ((fade-out-end (min (first (aref fadeclips 0))
|
||||
(first (aref fadeclips 1))))
|
||||
(fade-in-start (max (second (aref fadeclips 0))
|
||||
(second (aref fadeclips 1)))))
|
||||
(return
|
||||
(multichan-expand #'crossfade sig
|
||||
(- fade-out-end t0)
|
||||
(- fade-in-start t0)
|
||||
(- t1 t0))))
|
||||
(crossfade sig
|
||||
(- (first fadeclips) t0)
|
||||
(- (second fadeclips) t0)
|
||||
(- t1 t0))))
|
||||
|
||||
|
||||
;;; Run the program.
|
||||
(if (= (length (get '*selection* 'tracks)) 1)
|
||||
(catch 'error
|
||||
(process *track*
|
||||
(get '*selection* 'start)
|
||||
(get '*selection* 'end)
|
||||
(get '*track* 'clips)))
|
||||
"Error.\nCrossfade Clips may only be applied to one track.")
|
134
plug-ins/limiter.ny
Normal file
134
plug-ins/limiter.ny
Normal file
@ -0,0 +1,134 @@
|
||||
;nyquist plug-in
|
||||
;version 4
|
||||
;type process
|
||||
;categories "http://lv2plug.in/ns/lv2core/#DynamicsPlugin"
|
||||
;name "Limiter..."
|
||||
;action "Limiting..."
|
||||
;preview enabled
|
||||
;author "Steve Daulton"
|
||||
;copyright "Released under terms of the GNU General Public License version 2"
|
||||
|
||||
;; limiter.ny by Steve Daulton November 2011, updated May 2015.
|
||||
;; Released under terms of the GNU General Public License version 2:
|
||||
;; http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
|
||||
;;
|
||||
;; For information about writing and modifying Nyquist plug-ins:
|
||||
;; http://wiki.audacityteam.org/wiki/Nyquist_Plug-ins_Reference
|
||||
|
||||
;control type "Type" choice "Soft Limit,Hard Limit,Soft Clip,Hard Clip" 0
|
||||
;control gain-L "Input Gain (dB)\nmono/Left" real "" 0 0 10
|
||||
;control gain-R "Input Gain (dB)\nRight channel" real "" 0 0 10
|
||||
;control thresh "Limit to (dB)" real "" -3 -10 0
|
||||
;control hold "Hold (ms)" real "" 10 1 50
|
||||
;control makeup "Apply Make-up Gain" choice "No,Yes" 0
|
||||
|
||||
(if (not (boundp 'type))
|
||||
(setf type 0))
|
||||
|
||||
(if (boundp 'gain-L)
|
||||
(setf gain-L (db-to-linear gain-L))
|
||||
(setf gain-L 1))
|
||||
|
||||
(if (boundp 'gain-R)
|
||||
(setf gain-R (db-to-linear gain-R))
|
||||
(setf gain-R 1))
|
||||
|
||||
(if (boundp 'thresh)
|
||||
(setf thresh (db-to-linear thresh))
|
||||
(setf thresh (db-to-linear -3.0)))
|
||||
|
||||
(if (not (boundp 'hold))
|
||||
(setf hold 10.0))
|
||||
|
||||
(if (boundp 'makeup)
|
||||
(if (= makeup 1) (setf makeup T) (setf makeup nil))
|
||||
(setf makeup nil))
|
||||
|
||||
;;; brick wall limiter
|
||||
(defun hardlimit (sig limit hld)
|
||||
(let* ((time (/ hld 3000.0)) ; lookahead time (seconds)
|
||||
(samples (round (* time *sound-srate*))) ; lookahead in samples
|
||||
(peak-env (get-env sig samples time limit)))
|
||||
(mult sig
|
||||
(snd-exp
|
||||
(mult -1 (snd-log peak-env))))))
|
||||
|
||||
;;; Envelope follower for brick wall limiter
|
||||
(defun get-env (sig step lookahead limit)
|
||||
(let* ((sig (mult (/ limit) sig))
|
||||
(pad-time (* 3 lookahead)) ; padding required at start (seconds)
|
||||
(pad-s (* 3 step)) ; padding smaples
|
||||
(padding (snd-const (peak sig pad-s) 0 *sound-srate* pad-time))
|
||||
(peak-env (snd-avg sig (* 4 step) step OP-PEAK)))
|
||||
(extract 0 1
|
||||
(s-max 1
|
||||
(sim padding
|
||||
(at-abs pad-time (cue peak-env)))))))
|
||||
|
||||
(defun softlimit (sig thresh hld)
|
||||
(let* ((sig (hardlimit sig 1 hold))
|
||||
(step (truncate (* (/ hld 3000.0) *sound-srate*)))
|
||||
(waveshape (snd-avg sig (* 4 step) step op-peak))
|
||||
(env (sum thresh (mult thresh (diff 1 waveshape))))
|
||||
(env (clip env 1))
|
||||
(offset (/ (* 3 step) *sound-srate*))
|
||||
(initial (peak sig (* 2 step)))
|
||||
(pause-lev (sum thresh (mult thresh (diff 1 initial))))
|
||||
(pause-lev (clip pause-lev 0.9))
|
||||
(pause (snd-const pause-lev 0 *sound-srate* offset)))
|
||||
(setf env
|
||||
(sim
|
||||
pause
|
||||
(at-abs offset (cue env))))
|
||||
(mult sig env)))
|
||||
|
||||
|
||||
(defun soft-clip-table ()
|
||||
"Lookup table for soft clipping wave-shaper"
|
||||
(abs-env
|
||||
(Control-srate-abs *sound-srate*
|
||||
(let* ((knee (- 1 (/ 1.0 pi)))
|
||||
(kcurve (mult knee (osc (hz-to-step (/ (* 4 knee))) knee)))
|
||||
(ikcurve (mult knee (osc (hz-to-step (/ (* 4 knee))) knee *sine-table* -90)))
|
||||
(lin (pwlv -0.5 knee -0.5
|
||||
(+ knee (/ 2.0 pi)) 0.5
|
||||
2.0 0.5
|
||||
2.0 (+ 0.5 knee)
|
||||
2.1 (+ 0.5 knee))))
|
||||
(mult (/ 2.0 pi)
|
||||
(sim
|
||||
(at-abs 0 (cue ikcurve))
|
||||
(at-abs 0 (cue lin))
|
||||
(at-abs (+ knee (/ 2.0 pi)) (cue kcurve))))))))
|
||||
|
||||
(defun soft-clip (sig)
|
||||
(let* ((knee (- 1 (/ 1.0 pi)))
|
||||
(clip-level (* (+ 0.5 knee)(/ 2.0 pi)))
|
||||
(sig (mult clip-level (/ thresh) sig)))
|
||||
(if makeup
|
||||
(mult 0.999
|
||||
(/ clip-level)
|
||||
(shape sig (soft-clip-table) 1.0))
|
||||
(mult thresh
|
||||
(/ clip-level)
|
||||
(shape sig (soft-clip-table) 1.0)))))
|
||||
|
||||
|
||||
(defun makupgain (sig)
|
||||
(if makeup
|
||||
(mult (/ 0.999 thresh) sig) ;keep below 0dB
|
||||
sig))
|
||||
|
||||
;; Pre-gain
|
||||
(setf *track*
|
||||
(if (arrayp *track*)
|
||||
(vector (mult (aref *track* 0) gain-L)
|
||||
(mult (aref *track* 1) gain-R))
|
||||
(mult *track* gain-L)))
|
||||
|
||||
|
||||
(case type
|
||||
(0 (makupgain (multichan-expand #'softlimit *track* thresh hold)))
|
||||
(1 (makupgain (multichan-expand #'hardlimit *track* thresh hold)))
|
||||
(2 (soft-clip *track*))
|
||||
(T (makupgain (clip *track* thresh))))
|
@ -516,7 +516,7 @@ void PluginRegistrationDialog::PopulateOrExchange(ShuttleGui &S)
|
||||
{
|
||||
/*i18n-hint: The dialog shows a list of plugins with check-boxes
|
||||
beside each one.*/
|
||||
S.StartStatic(_("Select Plugins then press ENTER to Install"), true);
|
||||
S.StartStatic(_("Select Plugins, click the Enable or Disable button, then click OK."), true);
|
||||
{
|
||||
S.StartHorizontalLay(wxALIGN_LEFT,0 );
|
||||
{
|
||||
|
@ -781,7 +781,14 @@ AudacityProject::AudacityProject(wxWindow * parent, wxWindowID id,
|
||||
mMenuClose(false)
|
||||
, mbInitializingScrollbar(false)
|
||||
{
|
||||
mStatusBar = CreateStatusBar(3);
|
||||
// Note that the first field of the status bar is a dummy, and it's width is set
|
||||
// to zero latter in the code. This field is needed for wxWidgets 2.8.12 because
|
||||
// if you move to the menu bar, the first field of the menu bar is cleared, which
|
||||
// is undesirable behaviour.
|
||||
// In addition, the help strings of menu items are by default sent to the first
|
||||
// field. Currently there are no such help strings, but it they were introduced, then
|
||||
// there would need to be an event handler to send them to the appropriate field.
|
||||
mStatusBar = CreateStatusBar(4);
|
||||
|
||||
wxGetApp().SetMissingAliasedFileWarningShouldShow(true);
|
||||
|
||||
@ -1014,11 +1021,12 @@ AudacityProject::AudacityProject(wxWindow * parent, wxWindowID id,
|
||||
|
||||
mTrackFactory = new TrackFactory(mDirManager);
|
||||
|
||||
int widths[] = {GetControlToolBar()->WidthForStatusBar(), -2, -1};
|
||||
mStatusBar->SetStatusWidths(3, widths);
|
||||
int widths[] = {0, GetControlToolBar()->WidthForStatusBar(mStatusBar), -2, -1};
|
||||
mStatusBar->SetStatusWidths(4, widths);
|
||||
wxString msg = wxString::Format(_("Welcome to Audacity version %s"),
|
||||
AUDACITY_VERSION_STRING);
|
||||
mStatusBar->SetStatusText(msg, 1);
|
||||
mStatusBar->SetStatusText(msg, mainStatusBarField);
|
||||
mStatusBar->SetStatusText(GetControlToolBar()->StateForStatusBar(), stateStatusBarField);
|
||||
mLastStatusUpdateTime = ::wxGetUTCTime();
|
||||
|
||||
mTimer = new wxTimer(this, AudacityProjectTimerID);
|
||||
@ -3527,7 +3535,7 @@ bool AudacityProject::Save(bool overwrite /* = true */ ,
|
||||
wxRemoveFile(safetyFileName);
|
||||
|
||||
mStatusBar->SetStatusText(wxString::Format(_("Saved %s"),
|
||||
mFileName.c_str()), 1);
|
||||
mFileName.c_str()), mainStatusBarField);
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -4345,7 +4353,7 @@ void AudacityProject::OnTimer(wxTimerEvent& WXUNUSED(event))
|
||||
else
|
||||
msg.Printf(_("Out of disk space"));
|
||||
|
||||
mStatusBar->SetStatusText(msg, 1);
|
||||
mStatusBar->SetStatusText(msg, mainStatusBarField);
|
||||
}
|
||||
}
|
||||
else if(ODManager::IsInstanceCreated())
|
||||
@ -4366,7 +4374,7 @@ void AudacityProject::OnTimer(wxTimerEvent& WXUNUSED(event))
|
||||
|
||||
|
||||
msg.Printf(_("On-demand import and waveform calculation complete."));
|
||||
mStatusBar->SetStatusText(msg, 1);
|
||||
mStatusBar->SetStatusText(msg, mainStatusBarField);
|
||||
|
||||
}
|
||||
else if(numTasks>1)
|
||||
@ -4377,7 +4385,7 @@ void AudacityProject::OnTimer(wxTimerEvent& WXUNUSED(event))
|
||||
ratioComplete*100.0);
|
||||
|
||||
|
||||
mStatusBar->SetStatusText(msg, 1);
|
||||
mStatusBar->SetStatusText(msg, mainStatusBarField);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -4566,7 +4574,7 @@ void AudacityProject::EditClipboardByLabel( WaveTrack::EditDestFunction action )
|
||||
// TrackPanel callback method
|
||||
void AudacityProject::TP_DisplayStatusMessage(wxString msg)
|
||||
{
|
||||
mStatusBar->SetStatusText(msg, 1);
|
||||
mStatusBar->SetStatusText(msg, mainStatusBarField);
|
||||
mLastStatusUpdateTime = ::wxGetUTCTime();
|
||||
}
|
||||
|
||||
@ -4813,9 +4821,9 @@ void AudacityProject::OnAudioIORate(int rate)
|
||||
display = wxString::Format(_("Actual Rate: %d"), rate);
|
||||
int x, y;
|
||||
mStatusBar->GetTextExtent(display, &x, &y);
|
||||
int widths[] = {GetControlToolBar()->WidthForStatusBar(), -1, x+50};
|
||||
mStatusBar->SetStatusWidths(3, widths);
|
||||
mStatusBar->SetStatusText(display, 2);
|
||||
int widths[] = {0, GetControlToolBar()->WidthForStatusBar(mStatusBar), -1, x+50};
|
||||
mStatusBar->SetStatusWidths(4, widths);
|
||||
mStatusBar->SetStatusText(display, rateStatusBarField);
|
||||
}
|
||||
|
||||
void AudacityProject::OnAudioIOStartRecording()
|
||||
|
@ -109,6 +109,12 @@ enum PlayMode {
|
||||
loopedPlay
|
||||
};
|
||||
|
||||
enum StatusBarField {
|
||||
stateStatusBarField = 1,
|
||||
mainStatusBarField = 2,
|
||||
rateStatusBarField = 3
|
||||
};
|
||||
|
||||
// XML handler for <import> tag
|
||||
class ImportXMLTagHandler : public XMLTagHandler
|
||||
{
|
||||
|
@ -563,7 +563,7 @@ void ScreenFrame::DoCapture(wxString captureMode)
|
||||
|
||||
mCommand->SetParameter(wxT("CaptureMode"), captureMode);
|
||||
if (!mCommand->Apply(mContext))
|
||||
mStatus->SetStatusText(wxT("Capture failed!"), 1);
|
||||
mStatus->SetStatusText(wxT("Capture failed!"), mainStatusBarField);
|
||||
Show();
|
||||
}
|
||||
|
||||
|
@ -75,7 +75,7 @@ struct WaveDisplay
|
||||
Deallocate();
|
||||
}
|
||||
|
||||
void WaveDisplay::Allocate(int w)
|
||||
void Allocate(int w)
|
||||
{
|
||||
width = w;
|
||||
|
||||
@ -88,7 +88,7 @@ struct WaveDisplay
|
||||
bl = new int[width];
|
||||
}
|
||||
|
||||
void WaveDisplay::Deallocate()
|
||||
void Deallocate()
|
||||
{
|
||||
delete[] where;
|
||||
where = 0;
|
||||
|
@ -27,6 +27,7 @@ should be reference-counted.
|
||||
#include <wx/statusbr.h>
|
||||
#include "../widgets/ProgressDialog.h"
|
||||
#include "../commands/ResponseQueue.h"
|
||||
#include "../src/Project.h"
|
||||
|
||||
/// Interface for objects that can receive command progress information
|
||||
class CommandProgressTarget
|
||||
@ -117,7 +118,7 @@ public:
|
||||
{}
|
||||
virtual void Update(wxString message)
|
||||
{
|
||||
mStatus.SetStatusText(message, 1);
|
||||
mStatus.SetStatusText(message, mainStatusBarField);
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -2090,6 +2090,8 @@ bool VSTEffect::GetAutomationParameters(EffectAutomationParameters & parms)
|
||||
|
||||
bool VSTEffect::SetAutomationParameters(EffectAutomationParameters & parms)
|
||||
{
|
||||
size_t slaveCnt = mSlaves.GetCount();
|
||||
|
||||
callDispatcher(effBeginSetProgram, 0, 0, NULL, 0.0);
|
||||
for (int i = 0; i < mAEffect->numParams; i++)
|
||||
{
|
||||
@ -2105,7 +2107,14 @@ bool VSTEffect::SetAutomationParameters(EffectAutomationParameters & parms)
|
||||
return false;
|
||||
}
|
||||
|
||||
callSetParameter(i, d);
|
||||
if (d >= -1.0 && d <= 1.0)
|
||||
{
|
||||
callSetParameter(i, d);
|
||||
for (size_t i = 0; i < slaveCnt; i++)
|
||||
{
|
||||
mSlaves[i]->callSetParameter(i, d);
|
||||
}
|
||||
}
|
||||
}
|
||||
callDispatcher(effEndSetProgram, 0, 0, NULL, 0.0);
|
||||
|
||||
@ -2797,38 +2806,19 @@ bool VSTEffect::LoadParameters(const wxString & group)
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Value"), value, wxEmptyString))
|
||||
wxString parms;
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Parameters"), parms, wxEmptyString))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (callDispatcher(effBeginLoadProgram, 0, 0, &info, 0.0) == -1)
|
||||
EffectAutomationParameters eap;
|
||||
if (!eap.SetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
callDispatcher(effBeginSetProgram, 0, 0, NULL, 0.0);
|
||||
size_t cnt = mSlaves.GetCount();
|
||||
|
||||
wxStringTokenizer st(value, wxT(','));
|
||||
for (int i = 0; st.HasMoreTokens(); i++)
|
||||
{
|
||||
double val = 0.0;
|
||||
st.GetNextToken().ToDouble(&val);
|
||||
|
||||
if (val >= -1.0 && val <= 1.0)
|
||||
{
|
||||
callSetParameter(i, val);
|
||||
for (size_t i = 0; i < cnt; i++)
|
||||
{
|
||||
mSlaves[i]->callSetParameter(i, val);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
callDispatcher(effEndSetProgram, 0, 0, NULL, 0.0);
|
||||
|
||||
return true;
|
||||
return SetAutomationParameters(eap);
|
||||
}
|
||||
|
||||
bool VSTEffect::SaveParameters(const wxString & group)
|
||||
@ -2850,13 +2840,19 @@ bool VSTEffect::SaveParameters(const wxString & group)
|
||||
return true;
|
||||
}
|
||||
|
||||
wxString parms;
|
||||
for (int i = 0; i < mAEffect->numParams; i++)
|
||||
EffectAutomationParameters eap;
|
||||
if (!GetAutomationParameters(eap))
|
||||
{
|
||||
parms += wxString::Format(wxT(",%f"), callGetParameter(i));
|
||||
return false;
|
||||
}
|
||||
|
||||
return mHost->SetPrivateConfig(group, wxT("Value"), parms.Mid(1));
|
||||
wxString parms;
|
||||
if (!eap.GetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return mHost->SetPrivateConfig(group, wxT("Parameters"), parms);
|
||||
}
|
||||
|
||||
void VSTEffect::OnTimer()
|
||||
|
@ -1738,6 +1738,13 @@ bool AudioUnitEffect::SetAutomationParameters(EffectAutomationParameters & parms
|
||||
|
||||
delete [] array;
|
||||
|
||||
AudioUnitParameter aup;
|
||||
aup.mAudioUnit = mUnit;
|
||||
aup.mParameterID = kAUParameterListener_AnyParameter;
|
||||
aup.mScope = kAudioUnitScope_Global;
|
||||
aup.mElement = 0;
|
||||
AUParameterListenerNotify(NULL, NULL, &aup);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -2163,135 +2170,36 @@ void AudioUnitEffect::RemoveHandler()
|
||||
|
||||
bool AudioUnitEffect::LoadParameters(const wxString & group)
|
||||
{
|
||||
OSStatus result;
|
||||
UInt32 dataSize;
|
||||
Boolean isWritable;
|
||||
|
||||
wxString value;
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Value"), value, wxEmptyString))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
wxStringTokenizer tokens(value, wxT(','));
|
||||
|
||||
result = AudioUnitGetPropertyInfo(mUnit,
|
||||
kAudioUnitProperty_ParameterList,
|
||||
kAudioUnitScope_Global,
|
||||
0,
|
||||
&dataSize,
|
||||
&isWritable);
|
||||
if (result != noErr)
|
||||
wxString parms;
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Parameters"), parms, wxEmptyString))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
UInt32 cnt = dataSize / sizeof(AudioUnitParameterID);
|
||||
|
||||
if (cnt != tokens.CountTokens())
|
||||
EffectAutomationParameters eap;
|
||||
if (!eap.SetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
AudioUnitParameterID *array = new AudioUnitParameterID[cnt];
|
||||
|
||||
result = AudioUnitGetProperty(mUnit,
|
||||
kAudioUnitProperty_ParameterList,
|
||||
kAudioUnitScope_Global,
|
||||
0,
|
||||
array,
|
||||
&dataSize);
|
||||
if (result != noErr)
|
||||
{
|
||||
delete [] array;
|
||||
return false;
|
||||
}
|
||||
|
||||
for (int i = 0; i < cnt; i++)
|
||||
{
|
||||
double d = 0.0;
|
||||
tokens.GetNextToken().ToDouble(&d);
|
||||
|
||||
AudioUnitParameterValue value = d;
|
||||
result = AudioUnitSetParameter(mUnit,
|
||||
array[i],
|
||||
kAudioUnitScope_Global,
|
||||
0,
|
||||
value,
|
||||
0);
|
||||
if (result != noErr)
|
||||
{
|
||||
delete [] array;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
AudioUnitParameter aup;
|
||||
aup.mAudioUnit = mUnit;
|
||||
aup.mParameterID = kAUParameterListener_AnyParameter;
|
||||
aup.mScope = kAudioUnitScope_Global;
|
||||
aup.mElement = 0;
|
||||
AUParameterListenerNotify(NULL, NULL, &aup);
|
||||
|
||||
delete [] array;
|
||||
|
||||
return true;
|
||||
return SetAutomationParameters(eap);
|
||||
}
|
||||
|
||||
bool AudioUnitEffect::SaveParameters(const wxString & group)
|
||||
{
|
||||
OSStatus result;
|
||||
UInt32 dataSize;
|
||||
Boolean isWritable;
|
||||
EffectAutomationParameters eap;
|
||||
if (!GetAutomationParameters(eap))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
wxString parms;
|
||||
|
||||
result = AudioUnitGetPropertyInfo(mUnit,
|
||||
kAudioUnitProperty_ParameterList,
|
||||
kAudioUnitScope_Global,
|
||||
0,
|
||||
&dataSize,
|
||||
&isWritable);
|
||||
if (result != noErr)
|
||||
if (!eap.GetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
UInt32 cnt = dataSize / sizeof(AudioUnitParameterID);
|
||||
AudioUnitParameterID *array = new AudioUnitParameterID[cnt];
|
||||
|
||||
result = AudioUnitGetProperty(mUnit,
|
||||
kAudioUnitProperty_ParameterList,
|
||||
kAudioUnitScope_Global,
|
||||
0,
|
||||
array,
|
||||
&dataSize);
|
||||
if (result != noErr)
|
||||
{
|
||||
delete [] array;
|
||||
return false;
|
||||
}
|
||||
|
||||
for (int i = 0; i < cnt; i++)
|
||||
{
|
||||
AudioUnitParameterValue value;
|
||||
result = AudioUnitGetParameter(mUnit,
|
||||
array[i],
|
||||
kAudioUnitScope_Global,
|
||||
0,
|
||||
&value);
|
||||
if (result != noErr)
|
||||
{
|
||||
delete [] array;
|
||||
return false;
|
||||
}
|
||||
|
||||
parms += wxString::Format(wxT(",%f"), value);
|
||||
}
|
||||
|
||||
mHost->SetPrivateConfig(group, wxT("Value"), parms.Mid(1));
|
||||
|
||||
delete [] array;
|
||||
|
||||
return true;
|
||||
return mHost->SetPrivateConfig(group, wxT("Parameters"), parms);
|
||||
}
|
||||
|
||||
bool AudioUnitEffect::SetRateAndChannels()
|
||||
|
@ -1539,38 +1539,36 @@ void LadspaEffect::Unload()
|
||||
|
||||
bool LadspaEffect::LoadParameters(const wxString & group)
|
||||
{
|
||||
wxString value;
|
||||
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Value"), value, wxEmptyString))
|
||||
wxString parms;
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Parameters"), parms, wxEmptyString))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
wxStringTokenizer st(value, wxT(','));
|
||||
if (st.CountTokens() != mData->PortCount)
|
||||
EffectAutomationParameters eap;
|
||||
if (!eap.SetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
for (unsigned long p = 0; st.HasMoreTokens(); p++)
|
||||
{
|
||||
double val = 0.0;
|
||||
st.GetNextToken().ToDouble(&val);
|
||||
mInputControls[p] = val;
|
||||
}
|
||||
|
||||
return true;
|
||||
return SetAutomationParameters(eap);
|
||||
}
|
||||
|
||||
bool LadspaEffect::SaveParameters(const wxString & group)
|
||||
{
|
||||
wxString parms;
|
||||
for (unsigned long p = 0; p < mData->PortCount; p++)
|
||||
EffectAutomationParameters eap;
|
||||
if (!GetAutomationParameters(eap))
|
||||
{
|
||||
parms += wxString::Format(wxT(",%f"), mInputControls[p]);
|
||||
return false;
|
||||
}
|
||||
|
||||
return mHost->SetPrivateConfig(group, wxT("Value"), parms.Mid(1));
|
||||
wxString parms;
|
||||
if (!eap.GetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return mHost->SetPrivateConfig(group, wxT("Parameters"), parms);
|
||||
}
|
||||
|
||||
LADSPA_Handle LadspaEffect::InitInstance(float sampleRate)
|
||||
|
@ -1282,34 +1282,36 @@ void LV2Effect::ShowOptions()
|
||||
|
||||
bool LV2Effect::LoadParameters(const wxString & group)
|
||||
{
|
||||
wxString value;
|
||||
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Value"), value, wxEmptyString))
|
||||
wxString parms;
|
||||
if (!mHost->GetPrivateConfig(group, wxT("Parameters"), parms, wxEmptyString))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
wxStringTokenizer st(value, wxT(','));
|
||||
for (size_t p = 0; st.HasMoreTokens(); p++)
|
||||
EffectAutomationParameters eap;
|
||||
if (!eap.SetParameters(parms))
|
||||
{
|
||||
double val = 0.0;
|
||||
st.GetNextToken().ToDouble(&val);
|
||||
mControls[p].mVal = (float) val;
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
return SetAutomationParameters(eap);
|
||||
}
|
||||
|
||||
bool LV2Effect::SaveParameters(const wxString & group)
|
||||
{
|
||||
wxString parms;
|
||||
|
||||
for (size_t i = 0, cnt = mControls.GetCount(); i < cnt; i++)
|
||||
EffectAutomationParameters eap;
|
||||
if (!GetAutomationParameters(eap))
|
||||
{
|
||||
parms += wxString::Format(wxT(",%f"), mControls[i].mVal);
|
||||
return false;
|
||||
}
|
||||
|
||||
return mHost->SetPrivateConfig(group, wxT("Value"), parms.Mid(1));
|
||||
wxString parms;
|
||||
if (!eap.GetParameters(parms))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return mHost->SetPrivateConfig(group, wxT("Parameters"), parms);
|
||||
}
|
||||
|
||||
LV2_Options_Option *LV2Effect::AddOption(const char *key, uint32_t size, const char *type, void *value)
|
||||
|
@ -63,7 +63,7 @@ void TracksPrefs::Populate()
|
||||
mViewChoices.Add(_("Spectrogram"));
|
||||
mViewChoices.Add(_("Spectrogram log(f)"));
|
||||
mViewChoices.Add(_("Spectral Selection"));
|
||||
mViewChoices.Add(_("Spectrogram Selection log(f)"));
|
||||
mViewChoices.Add(_("Spectral Selection log(f)"));
|
||||
mViewChoices.Add(_("Pitch (EAC)"));
|
||||
|
||||
//------------------------- Main section --------------------
|
||||
|
@ -102,10 +102,10 @@ ControlToolBar::ControlToolBar()
|
||||
mCutPreviewTracks = NULL;
|
||||
|
||||
// strings for status bar
|
||||
mStatePlay = _("Playing");
|
||||
mStateStop = _("Stopped");
|
||||
mStateRecord = _("Recording");
|
||||
mStatePause = _("Paused");
|
||||
mStatePlay = XO("Playing");
|
||||
mStateStop = XO("Stopped");
|
||||
mStateRecord = XO("Recording");
|
||||
mStatePause = XO("Paused");
|
||||
}
|
||||
|
||||
ControlToolBar::~ControlToolBar()
|
||||
@ -1082,50 +1082,53 @@ void ControlToolBar::ClearCutPreviewTracks()
|
||||
}
|
||||
|
||||
// works out the width of the field in the status bar needed for the state (eg play, record pause)
|
||||
int ControlToolBar::WidthForStatusBar()
|
||||
int ControlToolBar::WidthForStatusBar(wxStatusBar* const sb)
|
||||
{
|
||||
AudacityProject* p = GetActiveProject();
|
||||
if (!p)
|
||||
return 100; // dummy value to keep things happy before the project is fully created
|
||||
|
||||
wxStatusBar* sb = p->GetStatusBar();
|
||||
int xMax = 0;
|
||||
int x, y;
|
||||
|
||||
sb->GetTextExtent(mStatePlay + wxT(" ") + mStatePause + wxT("."), &x, &y);
|
||||
sb->GetTextExtent(wxString(wxGetTranslation(mStatePlay)) + wxT(" ") +
|
||||
wxString(wxGetTranslation(mStatePause)) + wxT("."), &x, &y);
|
||||
if (x > xMax)
|
||||
xMax = x;
|
||||
|
||||
sb->GetTextExtent(mStateStop + wxT(" ") + mStatePause + wxT("."), &x, &y);
|
||||
sb->GetTextExtent(wxString(wxGetTranslation(mStateStop)) + wxT(" ") +
|
||||
wxString(wxGetTranslation(mStatePause)) + wxT("."), &x, &y);
|
||||
if (x > xMax)
|
||||
xMax = x;
|
||||
|
||||
sb->GetTextExtent(mStateRecord + wxT(" ") + mStatePause + wxT("."), &x, &y);
|
||||
sb->GetTextExtent(wxString(wxGetTranslation(mStateRecord)) + wxT(" ") +
|
||||
wxString(wxGetTranslation(mStatePause)) + wxT("."), &x, &y);
|
||||
if (x > xMax)
|
||||
xMax = x;
|
||||
|
||||
return xMax + 30; // added constant needed because xMax isn't large enough for some reason, plus some space.
|
||||
}
|
||||
|
||||
void ControlToolBar::UpdateStatusBar()
|
||||
wxString ControlToolBar::StateForStatusBar()
|
||||
{
|
||||
wxString state;
|
||||
|
||||
if (mPlay->IsDown())
|
||||
state = mStatePlay;
|
||||
state = wxGetTranslation(mStatePlay);
|
||||
else if (mRecord->IsDown())
|
||||
state = mStateRecord;
|
||||
state = wxGetTranslation(mStateRecord);
|
||||
else
|
||||
state = mStateStop;
|
||||
state = wxGetTranslation(mStateStop);
|
||||
|
||||
if (mPause->IsDown())
|
||||
{
|
||||
state.Append(wxT(" "));
|
||||
state.Append(mStatePause);
|
||||
state.Append(wxGetTranslation(mStatePause));
|
||||
}
|
||||
|
||||
state.Append(wxT("."));
|
||||
|
||||
GetActiveProject()->GetStatusBar()->SetStatusText(state);
|
||||
return state;
|
||||
}
|
||||
|
||||
void ControlToolBar::UpdateStatusBar()
|
||||
{
|
||||
GetActiveProject()->GetStatusBar()->SetStatusText(StateForStatusBar(), stateStatusBarField);
|
||||
}
|
||||
|
||||
|
@ -24,6 +24,7 @@ class wxKeyEvent;
|
||||
class wxTimer;
|
||||
class wxTimerEvent;
|
||||
class wxWindow;
|
||||
class wxStatusBar;
|
||||
|
||||
class AButton;
|
||||
class AudacityProject;
|
||||
@ -85,7 +86,8 @@ class ControlToolBar:public ToolBar {
|
||||
virtual void ReCreateButtons();
|
||||
void RegenerateToolsTooltips();
|
||||
|
||||
int WidthForStatusBar();
|
||||
int WidthForStatusBar(wxStatusBar* const);
|
||||
wxString StateForStatusBar();
|
||||
|
||||
private:
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user