Re: showdialog and 'Cannot access a disposed object'

Mike Andrews <[email protected]> Mon, 7 Jan 2008 07:49:46 -0600
Newsgroups gmane.comp.windows.devel.dotnet.winforms
Message-ID <[email protected]>
If you need to be able to specify a type for the "form" and then create it
if it's not been created yet or show it if it has, you can use generics to
your advantage here.

Create a method called CreateForm(Of T) or some such name like this:

    Public Class BaseForm
        Inherits System.Windows.Forms.Form
    End Class
    Private ShownForms As New Dictionary(Of String, BaseForm)
    Public Function CreateForm(Of ItemType As {BaseForm, New})() As ItemType
        Dim form As ItemType
        Dim key As String = GetType(ItemType).Name
        If Not ShownForms.ContainsKey(key) Then
            form = New ItemType()
            'Set other form parameters here
            ShownForms.Add(key, form)
        Else
            form = CType(ShownForms(key), ItemType)
        End If
        Return form
    End Function


On Jan 4, 2008 9:28 AM, chris Burgess <[email protected]> wrote:

> I have the following code to launch forms based upon a selection from
> a list box:
>
>  Private Sub LoadReport_Click(ByVal sender As System.Object, ByVal e
> As System.EventArgs) Handles LoadReport.Click
>        Dim rpt As New BaseReport
>        rpt = DirectCast(Me.Reports.SelectedValue, BaseReport)
>        rpt.ShowDialog()
>        rpt.Dispose()
>    End Sub
>
> 'Reports' is a list box that contains 'Report' objects. The Report
> object has a report name property (the DisplayMember) and a report
> form property, each of which is derived from BaseForm (the
> .valuemember).
>
> If I launch a report form, close it, then try to launch it again, I
> get an error:
>
> System.ObjectDisposedException was unhandled
>  Message="Cannot access a disposed object.
> Object name: 'Report_OrdersByDate'."
>  ObjectName="Report_OrdersByDate"
>  Source="System.Windows.Forms"
>  StackTrace:
>       at System.Windows.Forms.Control.CreateHandle()
>       at System.Windows.Forms.Form.CreateHandle()
>       at System.Windows.Forms.Control.get_Handle()
>       at System.Windows.Forms.Form.ShowDialog(IWin32Window owner)
>       at System.Windows.Forms.Form.ShowDialog()
>       at Converse.MainMenu.LoadReport_Click(Object sender, EventArgs
> e) in C:\Work\StoreReporter\StoreReporter\MainMenu.vb:line 48
>       at System.Windows.Forms.Control.OnClick(EventArgs e)
>       at System.Windows.Forms.Button.OnClick(EventArgs e)
>       at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent)
>       at System.Windows.Forms.Control.WmMouseUp(Message& m,
> MouseButtons button, Int32 clicks)
>       at System.Windows.Forms.Control.WndProc(Message& m)
>       at System.Windows.Forms.ButtonBase.WndProc(Message& m)
>       at System.Windows.Forms.Button.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
> (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 System.Windows.Forms.Application.Run(ApplicationContext context)
>       at
> Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.OnRun
> ()
>       at
> Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.DoApplicationModel
> ()
>       at
> Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase.Run
> (String[]
> commandLine)
>       at Converse.My.MyApplication.Main(String[] Args) in
> 17d14f5c-a337-4978-8281-53493378c1071.vb:line 81
>       at System.AppDomain.nExecuteAssembly(Assembly 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.Run(ExecutionContext
> executionContext, ContextCallback callback, Object state)
>       at System.Threading.ThreadHelper.ThreadStart()
>