2011-02-10 9 views
4

"Cannot access a disposed object. Object name: 'TreeView'." 오류와 관련하여 큰 문제가 있습니다.폐기 된 개체에 액세스 할 수 없습니다.

내 Windows 양식에서 나는 custom windows explorer object을 사용합니다.

그리고 여기가 내가 FlowLayoutPanel 선택한 디렉토리에있는 이미지를로드, 코드 부품 선택된 노드 이벤트에

을 온다. 폼 closing 이벤트 닫기 버튼 이벤트

Private Sub WizardControl1_CancelClick(ByVal sender As System.Object, ByVal e As System.ComponentModel.CancelEventArgs) Handles WizardControl1.CancelClick 
     Me.Close() 
End Sub 

에서

Private Sub ExpTree1_ExpTreeNodeSelected(ByVal SelPath As String, ByVal Item As ExplorerControls.CShItem) Handles ExpTree1.ExpTreeNodeSelected 
     'Loop until all images are loaded. 
     LoadImagesToFlowPreviewPanel() 
End Sub 

Private Sub Wizard_FormClosing(ByVal sender As Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing 
       Select Case XtraMessageBox.Show("Exit the application?", Me.Text, MessageBoxButtons.YesNo, MessageBoxIcon.Question) 
       Case Windows.Forms.DialogResult.No 
        e.Cancel = True 
       End Select 
     End If 
End Sub 

제가 적용 개폐 확인되면 LoadImagesToFlowPreviewPanel 서브 내의 코드가 계속 발견 디버깅하는 동안 실행하다. 모든 이미지가 FlowLayoutPanel 컨트롤에로드되면 오류가 발생합니다.

그리고 여기에 스택 추적이 온다 ...

at System.Windows.Forms.Control.CreateHandle() 
    at System.Windows.Forms.TreeView.CreateHandle() 
    at System.Windows.Forms.Control.get_Handle() 
    at System.Windows.Forms.TreeView.TvnSelected(NMTREEVIEW* nmtv) 
    at System.Windows.Forms.TreeView.WmNotify(Message& m) 
    at System.Windows.Forms.TreeView.WndProc(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.SendMessage(HandleRef hWnd, Int32 msg, IntPtr wParam, IntPtr lParam) 
    at System.Windows.Forms.Control.SendMessage(Int32 msg, IntPtr wparam, IntPtr lparam) 
    at System.Windows.Forms.Control.ReflectMessageInternal(IntPtr hWnd, Message& m) 
    at System.Windows.Forms.Control.WmNotify(Message& m) 
    at System.Windows.Forms.Control.WndProc(Message& m) 
    at System.Windows.Forms.Application.ParkingWindow.WndProc(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.CallWindowProc(IntPtr wndProc, IntPtr hWnd, Int32 msg, IntPtr wParam, IntPtr lParam) 
    at System.Windows.Forms.NativeWindow.DefWndProc(Message& m) 
    at System.Windows.Forms.TreeView.WmMouseDown(Message& m, MouseButtons button, Int32 clicks) 
    at System.Windows.Forms.TreeView.WndProc(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(Int32 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 Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.OnRun() 
    at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.DoApplicationModel() 
    at Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.Run(String[] commandLine) 
    at CannonUpdater.My.MyApplication.Main(String[] Args) in 17d14f5c-a337-4978-8281-53493378c1071.vb:line 82 
    at System.AppDomain._nExecuteAssembly(Assembly assembly, String[] args) 
    at System.Runtime.Hosting.ApplicationActivator.CreateInstance(ActivationContext activationContext, String[] activationCustomData) 
    at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssemblyDebugInZone() 
    at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state) 
    at System.Threading.ThreadHelper.ThreadStart() 

UPDATE : 모든 이미지가 FlowLayoutPanel에로드 된 응용 프로그램 가까이의 확인은 다음에 오는 경우, 내가 어떤 오류가 발생하지 않습니다.

+0

'LoadImagesToFlowPreviewPanel()'메서드는 어떻게됩니까? 별도의 스레드에서 실행하지 않는 한 해당 메서드가 실행을 마쳐야 양식을 닫을 수 없습니다. "모든 이미지가로드 될 때까지 루프"는 무엇입니까? 의견의 의미? 나는 루프를 보지 못한다 ... –

답변

4

LoadImagesToFlowPreviewPanel 방법의 관련 부분을 게시해야합니다.

이 투기 코드를 보지 않고,하지만 하나의 설명이 될 수 :

  • LoadImagesToFlowPreviewPanel는 통화 중 하나 동안 배치

  • 폼이 닫힌 루프와 트 리뷰에서 Application.DoEvents를 호출 to Application.DoEvents

  • 그러나 루프가 계속 실행되고 폐기 된 TreeView에 액세스합니다.

는이 있었다면, 용액 Application.DoEvents 호출 피하기 위해 재 설계 어느 것 또는 폼/트 리뷰가 Application.DoEvents 모든 호출 이후에 배치되어 닫혀 있으면, 적어도 검사. 응답

UPDATE는 언급합니다 :

와우! 당신은 당신의 코드에서 문제를 재진입 자신을 노출 Application.DoEvents 사용하는 경우 실제로 LoadImages 루프

내에서 Application.DoEvents를 호출 - 당신은 매우 조심해야하고 당신이 그것을 사용할 때 모든 결과를 이해 있는지 확인해야합니다 . 당신이 직면 할 수있는 유일한 문제는 당신이 설명한 문제는 아닙니다. 재진입 문제가 발생하지 않도록 보장 할 수있는 매우 구체적인 경우에만 사용합니다 (예 : 모달 진행 대화 상자가 표시되는 동안). 그리고 많은 사람들이 DoEvents을 "악마"라고 부를 것이고 전혀 상관하지 않을 것입니다.

+0

와우! 실제로 LoadImages는 루프 내에서'Application.DoEvents'를 호출합니다. – GeorgeBoy

+1

'DoEvents'는 "악의"이지만 반대는 * 심각한 코드 냄새입니다. 버그를 진단하기가 어려울 수 있으며 Windows 이벤트 기반 모델에 대한 이해가 부족함을 나타냅니다. 그것을 사용해야하는 유일한 사람들은 자신이하고있는 일에 대한 철저한 이해와 감사를 가진 사람들입니다. 이들은 종종 코드 작업을 수행하는 더 좋은 방법을 찾는 사람들과 같습니다. 처음부터 대답은 정확합니다. 나는 왜 지금까지 upvoted 유일한 사람이고 왜 받아 들여지지 않았는지 모르겠습니다. 귀하의 심령 디버거는 제 것보다 훨씬 잘 교정되었습니다. –

+0

@Cody - 전적으로 동의합니다. upvotes에 관해서는, 나의 경험은 일반적인 일반적인 질문에 대한 대답이 이런 특정한 것 이상으로 그들을 끌어 들이고 있다는 것입니다. 그러나 나는 내가 이제까지 쓸 수있는 것보다 많은 점을 가지고있어서 걱정하지 않는다. :) – Joe

3

기본적으로 사용자가 처리 한 개체에서 작업을 수행하면이 문제가 발생합니다. 그러니 이런 :

A a = new A(); 
a.Dispose(); 
//operations performed on a will fail now 

또는이

using(A a = new A()){ 
    ... 
} 
//operations performed on a will fail now 

같은

는 사용 블록도 단지 수동으로 Dispose를 호출 한 같은 개체를 처리 할 것을 기억하십시오.

0

여기서 무슨 일이 일어나는지는 TreeView 개체를 조작하는 스레드를 시작한 다음 스레드가 완료되기 전에 TreeView가 삭제되는 것입니다.

수정하려면 TreeView의 스레드에서 TreeView의 IsDisposed 속성을 사용하여 TreeView를 조작 할 수 있는지 또는 삭제하지 않았는지 확인하십시오.

관련 문제