为什么我在尝试操作图像文件时遇到无效的参数异常?

时间:2017-03-09 22:02:12

标签: c# .net winforms

private void DownloadCompletedCallback(object sender, AsyncCompletedEventArgs e)
        {
            if (e.Cancelled)
            {
                //... download cancelled...
            }
            else if (e.Error != null)
            {
                //... download failed...
                Logger.Write("Error: " + e.Error);
            }
            ActiveDownloadJob adJob = e.UserState as ActiveDownloadJob;
            ProgressBar pb = (adJob != null) ? adJob.ProgressBar : null;

            Image img = new Bitmap(adJob.DownloadData.TargetPath);
            Image[] frames = GetFramesFromAnimatedGIF(img);
            foreach(Image frame in frames)
            {
                frame.Save(@"c:\temp\tempframes\");
            }

            lock (_downloadQueue)
            {
                if (_downloadQueue.Count == 0)
                {
                    if (pb != null)
                    {
                        pb.Tag = null;
                        timer2.Stop();
                        timer3.Start();
                        label8.ForeColor = Color.Green;
                        label8.Text = "Process Finished";
                        mapsToolStripMenuItem.Enabled = true;
                        changeOutputDirectoryToolStripMenuItem.Enabled = true;
                        beginOperationToolStripMenuItem.Enabled = false;
                        viewDownloadedFilesToolStripMenuItem.Enabled = true;
                        Options_DB.Set_OperationLastTime(DateTime.Now.ToString());
                        playImages();
                        for (int i = 0; i < progressbars.Length; i++)
                        {
                            progressbars[i].Value = 0;
                        }
                        for (int x = 0; x < pbs.Length; x++)
                        {
                            if (x >= file_array.Length && pbs[x].Image == null)
                            {
                                pbs[x].Image = Properties.Resources.Weather_Michmoret;
                                pbs[x].Enabled = false;
                            }
                        }
                        for (int i = 0; i < file_array.Length; i++)
                        {
                            pbs[i].Animate(file_array[i]);
                            pbs[i].Enabled = true;
                            if (i == 7)
                                break;
                        }
                    }
                }
                else
                {
                    DownloadImages.DownloadData dd = _downloadQueue.Dequeue();
                    StartDownloadWithProgressBar(dd, pb);
                }
            }
        }

这是我试图从动画gif中保存每一帧的部分:

Image img = new Bitmap(adJob.DownloadData.TargetPath);
Image[] frames = GetFramesFromAnimatedGIF(img);
foreach(Image frame in frames)
{
  frame.Save(@"c:\temp\tempframes\");
}

使用断点的第一行传递正常。

然后它进入方法GetFramesFromAnimatedGIF

public static Image[] GetFramesFromAnimatedGIF(Image IMG)
        {
            List<Image> IMGs = new List<Image>();
            int Length = IMG.GetFrameCount(FrameDimension.Time);

            for (int i = 0; i < Length; i++)
            {
                IMG.SelectActiveFrame(FrameDimension.Time, i);
                IMGs.Add(new Bitmap(IMG));
                IMG.Dispose();
            }

            return IMGs.ToArray();
        }

我在返回行上放了一个断点:return IMGs.ToArray();

但它在某种程度上没有达到目的,它会抛出异常:

System.Reflection.TargetInvocationException was unhandled
  HResult=-2146232828
  Message=Exception has been thrown by the target of an invocation.
  Source=mscorlib
  StackTrace:
       at System.RuntimeMethodHandle.InvokeMethod(Object target, Object[] arguments, Signature sig, Boolean constructor)
       at System.Reflection.RuntimeMethodInfo.UnsafeInvokeInternal(Object obj, Object[] parameters, Object[] arguments)
       at System.Delegate.DynamicInvokeImpl(Object[] args)
       at System.Windows.Forms.Control.InvokeMarshaledCallbackDo(ThreadMethodEntry tme)
       at System.Windows.Forms.Control.InvokeMarshaledCallbackHelper(Object obj)
       at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
       at System.Windows.Forms.Control.InvokeMarshaledCallback(ThreadMethodEntry tme)
       at System.Windows.Forms.Control.InvokeMarshaledCallbacks()
       at System.Windows.Forms.Control.WndProc(Message& m)
       at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
       at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
       at System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)
       at System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg)
       at System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(IntPtr dwComponentID, Int32 reason, Int32 pvLoopData)
       at System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context)
       at System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context)
       at System.Windows.Forms.Application.Run(Form mainForm)
       at WeatherMaps.Program.Main() in D:\C-Sharp\WeatherMaps\WeatherMaps\WeatherMaps\Program.cs:line 19
       at System.AppDomain._nExecuteAssembly(RuntimeAssembly assembly, String[] args)
       at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
       at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
       at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
       at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean preserveSyncCtx)
       at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
       at System.Threading.ThreadHelper.ThreadStart()
  InnerException: 
       HResult=-2147024809
       Message=Parameter is not valid.
       Source=System.Drawing
       StackTrace:
            at System.Drawing.Image.SelectActiveFrame(FrameDimension dimension, Int32 frameIndex)
            at WeatherMaps.Form1.GetFramesFromAnimatedGIF(Image IMG) in Form1.cs:line 904
            at WeatherMaps.Form1.DownloadCompletedCallback(Object sender, AsyncCompletedEventArgs e) in Form1.cs:line 375
            at System.Net.WebClient.OnDownloadFileCompleted(AsyncCompletedEventArgs e)
            at System.Net.WebClient.DownloadFileOperationCompleted(Object arg)
       InnerException:

Form1第904行是:

IMG.SelectActiveFrame(FrameDimension.Time, i);

第375行是:

Image[] frames = GetFramesFromAnimatedGIF(img);

我可以在循环中看到Length值为10(10帧)。

1 个答案:

答案 0 :(得分:1)

您是否在第一次处理电话后检查了IMG的价值?您处理图像可能是它的原因,尝试调用现在无效的对象(不是FrameDimension类的专家,虽然我假设它是基于IMG对象创建的,因为我没有看到显式实例它是在快速浏览后创建的)