Community Forums Archive

Go Back

Subject:Help with batch pasting script
Posted by: roblesinge
Date:7/14/2010 12:02:27 PM

I put together this batch script to take all the files in a folder and paste the contents of the clipboard onto the end of each file. It worked in SF8, but for some reason won't run in SF10. Can anyone shed some light for me?

Script:

using System;

using System.IO;

using System.Windows.Forms;

using SoundForge;



public class EntryPoint {



public void Begin(IScriptableApp app) {



string strFolder = SfHelpers.ChooseDirectory("Choose a folder to process files from", @"S:\Audio");



foreach (string strFilename in Directory.GetFiles(strFolder, "*.wav"))

{

SfStatus status = ProcessFile(app, strFilename);

if (status != SfStatus.Success)

{

DPF("{0} : {1}", strFilename, status.ToString());

// quit if processing or save failed.

break;

}

}

}



public bool bEnableProcessingLog = true;



public SfStatus ProcessFile(IScriptableApp app, string strFilename)

{

if (bEnableProcessingLog)

DPF("processing {0}", strFilename);



ISfFileHost file = app.OpenFile(strFilename, false, true);

if (null == file)

return SfStatus.Fail;



file.WaitForDoneOrCancel();



// paste whatever audio is in the clipboard to the end of the current file.

// since DoMenu always operates on the active Data Window, we need to make

// sure that the file we want edited is active before using DoMenu().

file.Window.Active = true;

file.Window.Cursor = file.Length;

app.DoMenu("Edit.Paste", false);



// the other way to paste is OverwriteAudio(), but it requires a pasteFrom file..

// file.OverwriteAudio(file.Length, 0, fileToPasteFrom, new SfAudioSelection(fileToPasteFrom));



// wait for processing to complete, and if it succeeds, save the file

SfStatus status = file.WaitForDoneOrCancel();

if (status == SfStatus.Success)

{

file.Save(SaveOptions.PromptIfNoFilename);

status = file.WaitForDoneOrCancel();

}



file.Close(CloseOptions.DiscardChanges);

return status;

}





public void FromSoundForge(IScriptableApp app) {

ForgeApp = app; //execution begins here

app.SetStatusText(String.Format("Script '{0}' is running.", Script.Name));

Begin(app);

app.SetStatusText(String.Format("Script '{0}' is done.", Script.Name));

}

public static IScriptableApp ForgeApp = null;

public static void DPF(string sz) { ForgeApp.OutputText(sz); }

public static void DPF(string fmt, object o) { ForgeApp.OutputText(String.Format(fmt,o)); }

public static void DPF(string fmt, object o, object o2) { ForgeApp.OutputText(String.Format(fmt,o,o2)); }

public static void DPF(string fmt, object o, object o2, object o3) { ForgeApp.OutputText(String.Format

(fmt,o,o2,o3)); }

} //EntryPoint



This is the error I get:

System.Reflection.TargetInvocationException: Exception has been thrown by the target of an invocation. ---> System.NullReferenceException: Object reference not set to an instance of an object.
at EntryPoint.ProcessFile(IScriptableApp app, String strFilename)
at EntryPoint.Begin(IScriptableApp app)
at EntryPoint.FromSoundForge(IScriptableApp app)
--- End of inner exception stack trace ---
at System.RuntimeMethodHandle._InvokeMethodFast(Object target, Object[] arguments, SignatureStruct& sig, MethodAttributes methodAttributes, RuntimeTypeHandle typeOwner)
at System.RuntimeMethodHandle.InvokeMethodFast(Object target, Object[] arguments, Signature sig, MethodAttributes methodAttributes, RuntimeTypeHandle typeOwner)
at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture, Boolean skipVisibilityChecks)
at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture)
at SoundForge.ScriptHost.ScriptManager.Run(Assembly asm, String className, String methodName)

Thanks, as always!
--Rob.

Subject:RE: Help with batch pasting script
Reply by: roblesinge
Date:7/14/2010 12:51:17 PM

Since I'm having to revisit this script, I was going to attempt to change the pasting method from the DoMenu to OverwriteAudio, but I can't figure out how to get the fileToPasteFrom. I was thinking about using GetOpenFilename, but I can't figure out how to invoke it.

I'm still a scripting newb, so any help would be appreciated.

Rob.

Subject:RE: Help with batch pasting script
Reply by: roblesinge
Date:7/14/2010 2:57:40 PM

Okay, figured out that app.OpenFilename gets me the file to paste from. Now, I'm trying to figure out how to get that into the file.OverwriteAudio as my file to paste from. For some reason, it doesn't seem to exist where it's at now.

Here's what I've got so far:




using System;

using System.IO;

using System.Windows.Forms;

using SoundForge;



public class EntryPoint
{

public void Begin(IScriptableApp app)
{
string fPasteFrom = app.GetOpenFilename(@"S:\Audio");

string strFolder = SfHelpers.ChooseDirectory("Choose a folder to process files from", @"S:\Audio");

foreach (string strFilename in Directory.GetFiles(strFolder, "*.wav"))
{

SfStatus status = ProcessFile(app, strFilename);

if (status != SfStatus.Success)
{

DPF("{0} : {1}", strFilename, status.ToString());

// quit if processing or save failed.

break;

}

}

}



public bool bEnableProcessingLog = true;



public SfStatus ProcessFile(IScriptableApp app, string strFilename)
{

if (bEnableProcessingLog)

DPF("processing {0}", strFilename);



ISfFileHost file = app.OpenFile(strFilename, false, true);

if (null == file)

return SfStatus.Fail;



file.WaitForDoneOrCancel();


// the other way to paste is OverwriteAudio(), but it requires a pasteFrom file..

file.OverwriteAudio(file.Length, 0, fPasteFrom, new SfAudioSelection(fPasteFrom));



// wait for processing to complete, and if it succeeds, save the file

SfStatus status = file.WaitForDoneOrCancel();

if (status == SfStatus.Success)
{

file.Save(SaveOptions.PromptIfNoFilename);

status = file.WaitForDoneOrCancel();

}



file.Close(CloseOptions.DiscardChanges);

return status;

}





public void FromSoundForge(IScriptableApp app)
{

ForgeApp = app; //execution begins here

app.SetStatusText(String.Format("Script '{0}' is running.", Script.Name));

Begin(app);

app.SetStatusText(String.Format("Script '{0}' is done.", Script.Name));

}

public static IScriptableApp ForgeApp = null;

public static void DPF(string sz) { ForgeApp.OutputText(sz); }

public static void DPF(string fmt, object o) { ForgeApp.OutputText(String.Format(fmt, o)); }

public static void DPF(string fmt, object o, object o2) { ForgeApp.OutputText(String.Format(fmt, o, o2)); }

public static void DPF(string fmt, object o, object o2, object o3) { ForgeApp.OutputText(String.Format(fmt, o, o2, o3)); }

} //EntryPoint




The error I'm getting is:The name 'fPasteFrom' does not exist in the current context

Subject:RE: Help with batch pasting script
Reply by: roblesinge
Date:7/15/2010 6:58:43 AM

I got it! I needed to pass the fPasteFrom as an ISfFilehost object. So, I got this one working. I'm not completely sure I understand why it works this way, but it works.

Now, if I was going to alter this code to paste to the BEGINNING of the file, how would I alter that file.OverwriteAudio to make it paste to the beginning. I tried using "0" instead of "file.Length." But, it truly overwrites, instead of pasting. It seems like I need to set the cursor position to zero or the beginning somehow. Any help on that?

Here's the working code:




using System;

using System.IO;

using System.Windows.Forms;

using SoundForge;



public class EntryPoint
{

public void Begin(IScriptableApp app)
{
string fPasteFrom = app.GetOpenFilename(@"S:\Audio");
ISfFileHost pasteFile = app.OpenFile(fPasteFrom, true, false);

string strFolder = SfHelpers.ChooseDirectory("Choose a folder to process files from", @"S:\Audio");

foreach (string strFilename in Directory.GetFiles(strFolder, "*.wav"))
{

SfStatus status = ProcessFile(app, strFilename, pasteFile);

if (status != SfStatus.Success)
{

DPF("{0} : {1}", strFilename, status.ToString());

// quit if processing or save failed.

break;

}

}

}



public bool bEnableProcessingLog = true;



public SfStatus ProcessFile(IScriptableApp app, string strFilename, ISfFileHost fPasteFrom)
{

if (bEnableProcessingLog)

DPF("processing {0}", strFilename);



ISfFileHost file = app.OpenFile(strFilename, false, true);

if (null == file)

return SfStatus.Fail;



file.WaitForDoneOrCancel();


// the other way to paste is OverwriteAudio(), but it requires a pasteFrom file..

file.OverwriteAudio(file.Length, 0, fPasteFrom, new SfAudioSelection(fPasteFrom));



// wait for processing to complete, and if it succeeds, save the file

SfStatus status = file.WaitForDoneOrCancel();

if (status == SfStatus.Success)
{

file.Save(SaveOptions.PromptIfNoFilename);

status = file.WaitForDoneOrCancel();

}



file.Close(CloseOptions.DiscardChanges);

return status;

}





public void FromSoundForge(IScriptableApp app)
{

ForgeApp = app; //execution begins here

app.SetStatusText(String.Format("Script '{0}' is running.", Script.Name));

Begin(app);

app.SetStatusText(String.Format("Script '{0}' is done.", Script.Name));

}

public static IScriptableApp ForgeApp = null;

public static void DPF(string sz) { ForgeApp.OutputText(sz); }

public static void DPF(string fmt, object o) { ForgeApp.OutputText(String.Format(fmt, o)); }

public static void DPF(string fmt, object o, object o2) { ForgeApp.OutputText(String.Format(fmt, o, o2)); }

public static void DPF(string fmt, object o, object o2, object o3) { ForgeApp.OutputText(String.Format(fmt, o, o2, o3)); }

} //EntryPoint


Subject:RE: Help with batch pasting script
Reply by: ExSonyTJ
Date:7/16/2010 12:46:09 PM

You could use InsertAudio instead of OverwriteAudio

Subject:RE: Help with batch pasting script
Reply by: roblesinge
Date:7/16/2010 2:49:40 PM

That seems like it would make sense. However, I can't find any reference to "InsertAudio" in the SDK. Do you know where I could find it? Or, perhaps how to incorporate it into my code?

I ran across WriteAudio, which seems close to doing what I need done. Again, this seems to need the cursor placed at zero to work as a paste operation.

Thanks,
R.

Subject:RE: Help with batch pasting script
Reply by: ExSonyTJ
Date:7/19/2010 10:57:26 AM

Oops, you are correct, there is no InsertAudio function, to insert audio, you use ReplaceAudio with a destination selection that has 0 length. Or you use InsertSilence followed by OverwriteAudio. Something like this.


long ccInsert = 0; // 0 to insert a the beginning of the file.
file.ReplaceAudio(new SfAudioSelection(ccInsert, 0), fPasteFrom, new SfAudioSelection(fPasteFrom));


The WriteAudio method is for when you want to generate the audio data rather than read it from another file.

Message last edited on7/19/2010 10:58:10 AM byExSonyTJ.
Subject:RE: Help with batch pasting script
Reply by: roblesinge
Date:7/19/2010 2:57:05 PM

That's it! That did the trick. Thanks for the pointer on that one. I was stumped. Now I can focus on my file merging script. It's proving to be a bear. However, I'm thinking I can apply some of what I've found in putting these two scripts together.

Thanks for the help!
-Rob.

Go Back