J
james.jdunne
System.ArgumentException: Item has already been added. Key in
dictionary: "-1" Key being added: "-1"
at System.Collections.Hashtable.Insert(Object key, Object nvalue,
Boolean add)
at System.Collections.Hashtable.Add(Object key, Object value)
at
System.Windows.Forms.ComponentManager.System.Windows.Forms.UnsafeNativeMethods+IMsoComponentManager.FRegisterComponent(IMsoComponent
component, MSOCRINFOSTRUCT pcrinfo, Int32& dwComponentID)
at System.Windows.Forms.ThreadContext.get_ComponentManager()
at System.Windows.Forms.ThreadContext.RunMessageLoopInner(Int32
reason, ApplicationContext context)
at System.Windows.Forms.ThreadContext.RunMessageLoop(Int32 reason,
ApplicationContext context)
at System.Windows.Forms.Application.DoEvents()
I'm working with the Windows Media Encoder object library, needing to
call Application.DoEvents() to process the message pump to be notified
when an asynchronous encoding job completes. Unfortunately I cannot
reproduce the problem in a small complete example because it requires
the Windows Media Encoder SDK, but I will post my code nonetheless.
What I can tell you is that I'm running a two-threaded Windows.Forms
application that invokes the WMEncoder.Transcode() call from the
non-GUI thread. Also, I'm writing out a lot of output to a ListBox,
which could have been overfilled beyond 64K items. The non-GUI thread
properly calls back to the GUI thread via the BeginInvoke() procedure.
The application is basically a batch WMA file transcoder that processes
thousands of files during one instance of the application.
The following is the complete code for my transcoder wrapper class.
The exception is generated from the call to Application.DoEvents() in
the while (!done) loop.
using System;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace WMEncoderWrapper {
/// <summary>
/// Summary description for WMEncoder.
/// </summary>
public class WMEncoder {
private const int WMENC_CONTENT_ONE_AUDIO = 1;
private const int
WMA9STD_FOURCC = 353,
WMA9PRO_FOURCC = 354,
WMA9LSL_FOURCC = 355,
WMSPEECH_FOURCC = 10,
PCM_FOURCC = 0;
private bool done = false;
public WMEncoder() {
}
/// <summary>
/// Handles an encoder state change
/// </summary>
/// <param name="state"></param>
private void OnStateChange(WMEncoderLib.WMENC_ENCODER_STATE state) {
if (state == WMEncoderLib.WMENC_ENCODER_STATE.WMENC_ENCODER_STOPPED)
done = true;
}
/// <summary>
/// Transcode the input audio file (MP3, WMA, etc.) to a WMA9STD file
at 64kbps
/// </summary>
/// <param name="inputFile"></param>
/// <param name="outputFile"></param>
public void Transcode(string inputFile, string outputFile) {
WMEncoderLib.WMEncoder enc = null;
WMEncoderLib.IWMEncSourceGroup srcGroup = null;
WMEncoderLib.IWMEncSource src = null;
WMEncoderLib.IWMEncProfile2 profile = null;
WMEncoderLib.IWMEncAudienceObj audience = null;
try {
done = false;
// Create encoder:
enc = new WMEncoderLib.WMEncoderClass();
enc.OnStateChange += new
WMEncoderLib._IWMEncoderEvents_OnStateChangeEventHandler(OnStateChange);
profile = new WMEncoderLib.WMEncProfile2Class();
profile.ContentType = WMENC_CONTENT_ONE_AUDIO;
profile.ProfileName = "Profile1";
audience = profile.AddAudience(10000000);
// Set the encoding codec to WMA9STD with 1-pass CBR encoding:
int idxCodec =
profile.GetCodecIndexFromFourCC(WMEncoderLib.WMENC_SOURCE_TYPE.WMENC_AUDIO,
WMA9STD_FOURCC);
//profile.EnumAudioCodec(idxCodec, out codecName);
audience.set_AudioCodec(0, idxCodec);
// 2 channels, 44kHz sampling rate, 64,040bps bitrate, 16-bit
samples
audience.SetAudioConfig(0, 2, 44100, 64040, 16);
// Create a source group:
srcGroup = enc.SourceGroupCollection.Add("SG_1");
srcGroup.set_Profile(profile);
// Set the input file:
src =
srcGroup.AddSource(WMEncoderLib.WMENC_SOURCE_TYPE.WMENC_AUDIO);
src.SetInput(inputFile, String.Empty, String.Empty);
// Set the output file:
enc.File.LocalFileName = outputFile;
// Transcode:
enc.AutoStop = true;
enc.PrepareToEncode(true);
enc.Start();
// Wait until encoding stops:
while (!done) {
Application.DoEvents();
// Yield to other threads.
System.Threading.Thread.Sleep(0);
}
enc.Stop();
} finally {
if (enc != null) Marshal.ReleaseComObject(enc);
if (srcGroup != null) Marshal.ReleaseComObject(srcGroup);
if (src != null) Marshal.ReleaseComObject(src);
if (profile != null) Marshal.ReleaseComObject(profile);
if (audience != null) Marshal.ReleaseComObject(audience);
}
}
}
}
I've seen others in this newsgroup post about similar problems but with
no resolve on the issue. Can someone investigate this problem?
dictionary: "-1" Key being added: "-1"
at System.Collections.Hashtable.Insert(Object key, Object nvalue,
Boolean add)
at System.Collections.Hashtable.Add(Object key, Object value)
at
System.Windows.Forms.ComponentManager.System.Windows.Forms.UnsafeNativeMethods+IMsoComponentManager.FRegisterComponent(IMsoComponent
component, MSOCRINFOSTRUCT pcrinfo, Int32& dwComponentID)
at System.Windows.Forms.ThreadContext.get_ComponentManager()
at System.Windows.Forms.ThreadContext.RunMessageLoopInner(Int32
reason, ApplicationContext context)
at System.Windows.Forms.ThreadContext.RunMessageLoop(Int32 reason,
ApplicationContext context)
at System.Windows.Forms.Application.DoEvents()
I'm working with the Windows Media Encoder object library, needing to
call Application.DoEvents() to process the message pump to be notified
when an asynchronous encoding job completes. Unfortunately I cannot
reproduce the problem in a small complete example because it requires
the Windows Media Encoder SDK, but I will post my code nonetheless.
What I can tell you is that I'm running a two-threaded Windows.Forms
application that invokes the WMEncoder.Transcode() call from the
non-GUI thread. Also, I'm writing out a lot of output to a ListBox,
which could have been overfilled beyond 64K items. The non-GUI thread
properly calls back to the GUI thread via the BeginInvoke() procedure.
The application is basically a batch WMA file transcoder that processes
thousands of files during one instance of the application.
The following is the complete code for my transcoder wrapper class.
The exception is generated from the call to Application.DoEvents() in
the while (!done) loop.
using System;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace WMEncoderWrapper {
/// <summary>
/// Summary description for WMEncoder.
/// </summary>
public class WMEncoder {
private const int WMENC_CONTENT_ONE_AUDIO = 1;
private const int
WMA9STD_FOURCC = 353,
WMA9PRO_FOURCC = 354,
WMA9LSL_FOURCC = 355,
WMSPEECH_FOURCC = 10,
PCM_FOURCC = 0;
private bool done = false;
public WMEncoder() {
}
/// <summary>
/// Handles an encoder state change
/// </summary>
/// <param name="state"></param>
private void OnStateChange(WMEncoderLib.WMENC_ENCODER_STATE state) {
if (state == WMEncoderLib.WMENC_ENCODER_STATE.WMENC_ENCODER_STOPPED)
done = true;
}
/// <summary>
/// Transcode the input audio file (MP3, WMA, etc.) to a WMA9STD file
at 64kbps
/// </summary>
/// <param name="inputFile"></param>
/// <param name="outputFile"></param>
public void Transcode(string inputFile, string outputFile) {
WMEncoderLib.WMEncoder enc = null;
WMEncoderLib.IWMEncSourceGroup srcGroup = null;
WMEncoderLib.IWMEncSource src = null;
WMEncoderLib.IWMEncProfile2 profile = null;
WMEncoderLib.IWMEncAudienceObj audience = null;
try {
done = false;
// Create encoder:
enc = new WMEncoderLib.WMEncoderClass();
enc.OnStateChange += new
WMEncoderLib._IWMEncoderEvents_OnStateChangeEventHandler(OnStateChange);
profile = new WMEncoderLib.WMEncProfile2Class();
profile.ContentType = WMENC_CONTENT_ONE_AUDIO;
profile.ProfileName = "Profile1";
audience = profile.AddAudience(10000000);
// Set the encoding codec to WMA9STD with 1-pass CBR encoding:
int idxCodec =
profile.GetCodecIndexFromFourCC(WMEncoderLib.WMENC_SOURCE_TYPE.WMENC_AUDIO,
WMA9STD_FOURCC);
//profile.EnumAudioCodec(idxCodec, out codecName);
audience.set_AudioCodec(0, idxCodec);
// 2 channels, 44kHz sampling rate, 64,040bps bitrate, 16-bit
samples
audience.SetAudioConfig(0, 2, 44100, 64040, 16);
// Create a source group:
srcGroup = enc.SourceGroupCollection.Add("SG_1");
srcGroup.set_Profile(profile);
// Set the input file:
src =
srcGroup.AddSource(WMEncoderLib.WMENC_SOURCE_TYPE.WMENC_AUDIO);
src.SetInput(inputFile, String.Empty, String.Empty);
// Set the output file:
enc.File.LocalFileName = outputFile;
// Transcode:
enc.AutoStop = true;
enc.PrepareToEncode(true);
enc.Start();
// Wait until encoding stops:
while (!done) {
Application.DoEvents();
// Yield to other threads.
System.Threading.Thread.Sleep(0);
}
enc.Stop();
} finally {
if (enc != null) Marshal.ReleaseComObject(enc);
if (srcGroup != null) Marshal.ReleaseComObject(srcGroup);
if (src != null) Marshal.ReleaseComObject(src);
if (profile != null) Marshal.ReleaseComObject(profile);
if (audience != null) Marshal.ReleaseComObject(audience);
}
}
}
}
I've seen others in this newsgroup post about similar problems but with
no resolve on the issue. Can someone investigate this problem?