Community Forums Archive

Go Back

Subject:scripting residue...
Posted by: D-Slam
Date:8/15/2006 9:50:59 AM

I know there's been a lot of discussion about sfk files and such. I do have my settings so SF deletes them on close (which is great).

The thing is, for some reason, after running automated scripts, and then closing SF, these files don't get deleted.

Is there A) some point in my script where I could force a clean-up? or B) Something I should look for that might be keeping these files "in use"?

I began from the SoundForgeExample code. Should I be doing something when the app unloads? -


// Audio C# Solution
// run from Sound Forge
// (scripting available in Sound Forge 8.0d or higher)
//
// Last Modified: 6/13/2006
// --------------------------------------------------------------------
//
//
//Use Visual Studio for debugging:
// SETUP
// Assembly
// 1. Under asssembly ForgeScript, Properties, Configuration Properties, Debugging
// - verify that the Debug Mode is Program
// - Start Application = full path to Sound Forge EXE, including EXE
// - Working Directory = path to Sound Forge EXE
// References
// 1. Confirm that the path to Forge80.Script.dll is correct for your pc. If not, remove
// it and re-add it.
//
// DEBUGGING
// 1. Rebuild your solution
// 2. Add breakpoints as desired
// 3. Start Debug (F5) to launch Sound Forge
// 4. From Sound Forge, select the menu Tools | Scripting, then Run Script
// 5. Navigate to the location of the NAT.dll and click Open
// 6. Visual Studio will run to your first breakpoint
// 7. Exit Sound Forge to finish debugging
//-------------------------------------------------------------


using System;
using System.IO;
using System.Windows.Forms;
using System.Text;
using SoundForge;
using Utility.ModifyRegistry;

/// <summary>
/// Entry Point for Sound Forge
/// In order for Forge to run the C# DLL, the class EntryPoint MUST exist outside of the namespace
/// </summary>
public class EntryPoint
{
/// <summary>
/// Launches the primary class for this project &
/// </summary>
/// <param name="app"></param>
public void FromSoundForge(IScriptableApp app)
{
ForgeApp = app;
app.SetStatusText(String.Format("Script '{0}' is running.", Script.Name));
NAT.Engine.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)); }
}// EntryPoint


namespace NAT
{
public class Engine
{
private static MainForm form;
/// <summary>
/// Launches the GUI
/// </summary>
public static void Begin(SoundForge.IScriptableApp app)
{
// Initialize the form & show it
form = new MainForm(app);
form.ShowDialog();
}
}
}

// Then here's a bit more...

using System;
using ...

namespace NAT
{
/// <summary>
/// Summary description for MainForm.
/// </summary>
public class MainForm : System.Windows.Forms.Form
{
private System.Windows.Forms.Panel panel1;
private System.Windows.Forms.etc .....

/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.Container components = null;

/// <summary>
/// Constructor for MainForm
/// </summary>
/// <param name="app"></param>
public MainForm(SoundForge.IScriptableApp app)
{
//
// Required for Windows Form Designer support
//
InitializeComponent();

EntryPoint.DPF("Postprocessing");
}

/// <summary>
/// Clean up any resources being used.
/// </summary>
protected override void Dispose( bool disposing )
{
if( disposing )
{
if(components != null)
{
components.Dispose();
}
}
base.Dispose( disposing );
}

#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
...
}
#endregion

}
}






I did try creating an event that fires when MainForm closes, but things are still tied up at that point. I could use some tips.

Thanks!

Message last edited on8/15/2006 11:21:28 AM byD-Slam.
Subject:RE: scripting residue...
Reply by: _TJ
Date:8/16/2006 10:26:49 AM

This script template looks just fine. The bad news is that as Sound Forge won't do it's post-script cleanup until your script exits. Trying to get a shot at executing AFTER Sound Forge cleanup is just going to mess things up.

There also appears to be circumstances where the garbage collection of script objects results in some references still being held on Sound Forge ISfFileHost objects after a script has exited. Why this happens, we don't know, the ways of the GN are mysterious and too subtle for the mind of mankind to understand.

But we have seen it happen, and, so far. I haven't been able to find a way to force cleanup. manually forcing a garbage collect doesn't solve the problem.

So, your best bet for now is to try and open files with fNoWindow=true whenever possible (this defeats peak file creation).

The only other way I could think of to do cleanup would be for your script to start another process that waits for Sound Forge to exit, then goes around killing off the residue.

tj

Subject:RE: scripting residue...
Reply by: D-Slam
Date:8/17/2006 8:58:44 AM

OK cool. I like it.

Can you say a little more about fNoWindow=true. My current call already sets it to true.

// OPEN THE FILE
ISfFileHost file = app.OpenFile(strFilename, false, true);

Oddly, the docs say it MUST be false...

<h4>Parameters</h4>
pszFileName: The full path to the file. If the file is already open, the existing ISfFileHost is returned instead of creating a new one.
fReadOnly: True to open for read-only access. This parameter is ignored if the file is already open.
fNoWindow: Must be false. True is for future use.


Also, it looks like little .tmp (undo?) files are being created for EACH STEP of the post processing (and there are several!). So even when I'm processing a handful of files, I get that number of temp files several tiomes over. Obviously if you're doing ~1000 files, this can get pretty barfy.

Is there a way to turn off undo (assuming that's the issue)?

You're the mightiest.

Message last edited on8/17/2006 9:12:38 AM byD-Slam.
Subject:RE: scripting residue...
Reply by: _TJ
Date:8/17/2006 10:45:08 AM

fNoWindow was intended to actually create a file without a corresponding ISfDataWnd. It was marked as 'future' because many of the processing functions
would crash or misbehave if the window was missing. So we were going to re-factor all of the processing functions to work without a window, and then enable fNoWindow. Sometime in the future.

However, testing with the Batch Converter, we realized that building .sfk files was really hurting performance, so we implemented fNoWindow partially. Basically it creates the ISfDataWnd, but it's only partially functional. In particular, it never draws the data, so it never causes a .SFK file to be created.

At some point in the future, fNoWindow might change to actually create a ISfFileHost an associated ISfDataWnd, but for now it just creates one that the user can't interact with.

So, ONLY use fNoWindow when you plan to close the files in your script before your script exits. It defeats .sfk building, and creates a window that the user can't work with.

As for turning off undo's. That's easy. Just set
ISfFileHost.UndosAreEnabled = false right after you open the file.

tj


Go Back