Old 01-13-2015, 01:45 PM   #1
Argitoth
Human being with feelings
 
Argitoth's Avatar
 
Join Date: Feb 2008
Location: Phoenix, AZ
Posts: 2,055
Default AudioAccessor when dealing with multichannel makes NO SENSE.

latest attempt:
Code:
vector<string> &split(const string &s, char delim, vector<string> &elems){
	stringstream ss(s);
	string item;
	while (getline(ss, item, delim)) {
		elems.push_back(item);
	}
	return elems;
}

vector<string> split(const string &s, char delim){
	vector<string> elems;
	split(s, delim, elems);
	return elems;
}
Code:
void ActionTrimSilence()
{
	items = CountSelectedMediaItems(0) ;
  if (!items) return;

	if (HasExtState("Last_Used_Settings","TrimSilence_where")) sprintf_s(charbuf,FNLEN,"%s,%s,%s,%s,%s",
		GetExtState("Last_Used_Settings","TrimSilence_dB"),
		GetExtState("Last_Used_Settings","TrimSilence_sec"),
		GetExtState("Last_Used_Settings","TrimSilence_skip"),
		GetExtState("Last_Used_Settings","TrimSilence_chan"),
		GetExtState("Last_Used_Settings","TrimSilence_where"));
	else strcpy(charbuf,"-100,.5,.05,1,0");

	if (GetUserInputs("Trim Silence",5,"threshold(dB),threshold(sec),skip first x sec,analyze channel (1st=1),before=0 after=1 thresh. time",charbuf,FNLEN)){		
		vector<string> Input = split(charbuf, ',');	

		sprintf_s(charbuf,FNLEN,"Removing silence of %i items...", items); ShowConsoleMsg(charbuf);		

		PreventUIRefresh(-1);
		Undo_BeginBlock();
		for (int i=0; i < items; ++i){
			MediaItem*      item      = GetSelectedMediaItem(0, i);
			MediaItem_Take* take      = GetActiveTake(item);
			PCM_source*     source    = GetMediaItemTake_Source(take);
			double          position  = GetMediaItemInfo_Value(item, "D_POSITION");
			double          length    = GetMediaItemInfo_Value(item, "D_LENGTH");      
			double          offset    = GetMediaItemTakeInfo_Value(take, "D_STARTOFFS");			
			double          srate     = source->GetSampleRate();
			int             nch       = source->GetNumChannels();		
			double          sourcelen = source->GetLength();
			int             chanmode  = GetMediaItemTakeInfo_Value(take, "I_CHANMODE");

			// user values			
			double minAmp   = pow(2,stod(Input[0])/6);          //dB to amplitude
			int    maxTime  = max(1,stod(Input[1])*srate); //samples
			double skipTime = stod(Input[2]);                   //seconds
			int    chan     = max(0,stoi(Input[3])-1);          //wav channel to analyze
			bool   at       = stob(Input[4]);                   //switch where to trim
			int    samples  = max(0,(min(length,sourcelen)-skipTime))*srate;

			if (length < skipTime) continue;

			// audio accessor
			SetMediaItemTakeInfo_Value(take, "I_CHANMODE", 0);
			double* buffer = new double[(samples*nch)];
			AudioAccessor* accessor = CreateTakeAudioAccessor(take);
		  GetAudioAccessorSamples(accessor, srate, nch, skipTime, samples, buffer);
			DestroyAudioAccessor(accessor);
			       
			int    s=chan; //sample position			
			double v=0;    //sample value
			int    t=0;    //num sample values less than minAmp      
			while (s < samples){
				v = fabs(buffer[s]);
				if (v < minAmp) t+=1;
				else t=0;
				if (t > maxTime) break;
				s+=nch;
			}
			s/=nch;
			delete buffer;			
			double newlen = skipTime + (at ? s : s-t) / srate;

			SetMediaItemLength(item, newlen, 1);
			SetMediaItemTakeInfo_Value(take, "I_CHANMODE", chanmode);
		}
		ShowConsoleMsg("COMPLETE!\n\n");
		Undo_EndBlock("Trim silence",-1);
		PreventUIRefresh(1);
		UpdateArrange();
		SetExtState("Last_Used_Settings", "TrimSilence_dB", Input[0].c_str(), 1);
		SetExtState("Last_Used_Settings", "TrimSilence_sec", Input[1].c_str(), 1);
		SetExtState("Last_Used_Settings", "TrimSilence_skip", Input[2].c_str(), 1);
		SetExtState("Last_Used_Settings", "TrimSilence_chan", Input[3].c_str(), 1);
		SetExtState("Last_Used_Settings", "TrimSilence_where", Input[4].c_str(), 1);
	}
}
__________________
Soundemote - Home of the chaosfly and pretty oscilloscope.
MyReaperPlugin - Easy-to-use cross-platform C++ REAPER extension template

Last edited by Argitoth; 01-13-2015 at 06:59 PM.
Argitoth is offline   Reply With Quote
Old 01-13-2015, 02:43 PM   #2
Xenakios
Human being with feelings
 
Xenakios's Avatar
 
Join Date: Feb 2007
Location: Oulu, Finland
Posts: 7,913
Default

I can't quickly test this now. But to cover the obvious stuff...You have a large enough buffer for the audio? You are going through the audio in the correct order and speed?
__________________
For info on SWS Reaper extension plugin (including Xenakios' previous extension/actions) :
http://www.sws-extension.org/
https://github.com/Jeff0S/sws
--
Xenakios blog (about HourGlass, Paul(X)Stretch and λ) :
http://xenakios.wordpress.com/
Xenakios is offline   Reply With Quote
Old 01-13-2015, 03:06 PM   #3
Xenakios
Human being with feelings
 
Xenakios's Avatar
 
Join Date: Feb 2007
Location: Oulu, Finland
Posts: 7,913
Default

I am too tired to read it carefully and test it now, but as a quickie possibility : try using fabs instead of abs in your analysis loop. I have had some really weird issues in the past when using abs. That likely won't help but at least it's something to try...
__________________
For info on SWS Reaper extension plugin (including Xenakios' previous extension/actions) :
http://www.sws-extension.org/
https://github.com/Jeff0S/sws
--
Xenakios blog (about HourGlass, Paul(X)Stretch and λ) :
http://xenakios.wordpress.com/
Xenakios is offline   Reply With Quote
Old 01-13-2015, 03:12 PM   #4
Argitoth
Human being with feelings
 
Argitoth's Avatar
 
Join Date: Feb 2008
Location: Phoenix, AZ
Posts: 2,055
Default

download: http://www.elanhickler.com/transfer/...channel_DC.wav

download: http://www.elanhickler.com/transfer/...l_DC_faded.wav

download: http://www.elanhickler.com/transfer/...l_test_sin.wav

edit: no change with fabs
__________________
Soundemote - Home of the chaosfly and pretty oscilloscope.
MyReaperPlugin - Easy-to-use cross-platform C++ REAPER extension template

Last edited by Argitoth; 01-13-2015 at 07:45 PM.
Argitoth is offline   Reply With Quote
Old 01-13-2015, 07:23 PM   #5
Argitoth
Human being with feelings
 
Argitoth's Avatar
 
Join Date: Feb 2008
Location: Phoenix, AZ
Posts: 2,055
Default

WORKS
Code:
			double v=0;    //sample value
			int    t=0;    //num sample values less than minAmp    
			int s;
			for (s = 0; s < samples; ++s) {
				v = fabs(buffer[s*nch+chan]);
				if (v < minAmp) t+=1;
				else t=0;
				if (t > maxTime) break;
			}
			delete buffer;			
			double newlen = skipTime + (at ? s : s-t) / srate;
DOES NOT WORK
Code:
			int    s=chan; //sample position			
			double v=0;    //sample value
			int    t=0;    //num sample values less than minAmp      
			while (s < samples){
				v = fabs(buffer[s]);
				if (v < minAmp) t+=1;
				else t=0;
				if (t > maxTime) break;
				s+=nch;
			}
			s/=nch;
			delete buffer;			
			double newlen = skipTime + (at ? s : s-t) / srate;
__________________
Soundemote - Home of the chaosfly and pretty oscilloscope.
MyReaperPlugin - Easy-to-use cross-platform C++ REAPER extension template

Last edited by Argitoth; 01-13-2015 at 09:11 PM.
Argitoth is offline   Reply With Quote
Reply

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT -7. The time now is 08:51 PM.


Powered by vBulletin® Version 3.8.11
Copyright ©2000 - 2019, vBulletin Solutions Inc.