FolderBrowserDialog sur un projet MDI

Signaler
Messages postés
38
Date d'inscription
mardi 1 août 2006
Statut
Membre
Dernière intervention
9 juillet 2013
-
Messages postés
420
Date d'inscription
vendredi 17 novembre 2006
Statut
Membre
Dernière intervention
15 juillet 2014
-
Bonjour,

Je suis sur un FolderBrowserDialog qui me pose un serieux problème.

J'ai créé un projet MDI et lors de l'exécution de la sub suivante :


Public Sub BrowseBprDir()


Dim BrwseBpr As New FolderBrowserDialog

BrwseBpr.RootFolder = Environment.SpecialFolder.Desktop
BrwseBpr.Description = "Sélectionnez un répertoire"
BrwseBpr.ShowDialog()'<----------ERREUR ICI
If BrwseBpr.SelectedPath = String.Empty Then
MsgBox("Pas de sélection")
Else

MsgBox(BrwseBpr.SelectedPath)

End If
BrwseBpr.Dispose()
End Sub


j'ai ce message d'erreur :

Current thread must be set to single thread apartment (STA) mode before OLE calls can be made. Ensure that your Main function has STAThreadAttribute marked on it. This exception is only raised if a debugger is attached to the process.

J'ai fouillé un peu partout et j'ai trouvé un e réponse sur le net defaire un Invoke.

Je ne sais pas comment m'en dépatouiller. Je ne comprend pas.
J'ai essayé de voir avec STAThreadAttribute mais mis a part un mal de crâne... rien.

Est-ce que quelqu'un peut me venir en aide ???

Merci d'avance.

@+ Thierry

3 réponses

Messages postés
420
Date d'inscription
vendredi 17 novembre 2006
Statut
Membre
Dernière intervention
15 juillet 2014
6
Bonjour,

Voici une solution pour résoudre le problème d'appelle par un thread non STA

Public Delegate Sub BrowseBprDirDelegate()
    Public Sub BrowseBprDir()
        If Me.InvokeRequired Then
            Me.Invoke(New BrowseBprDirDelegate(AddressOf BrowseBprDir))
        Else
            Dim BrwseBpr As New FolderBrowserDialog

            BrwseBpr.RootFolder = Environment.SpecialFolder.Desktop
            BrwseBpr.Description = "Sélectionnez un répertoire"
            BrwseBpr.ShowDialog() '<----------ERREUR ICI 
            If BrwseBpr.SelectedPath = String.Empty Then
                MsgBox("Pas de sélection")
            Else

                MsgBox(BrwseBpr.SelectedPath)

            End If
            BrwseBpr.Dispose()
        End If

    End Sub


Utilisez la méthode BrowseBprDir() de la même manière, c'est elle (Me.InvokeRequired) qui fera un invoke si nécessaire.

Si cette solution ne fonctionne pas, il faudra préciser à quel moment vous appelez la méthode BrowseBprDir()
Messages postés
38
Date d'inscription
mardi 1 août 2006
Statut
Membre
Dernière intervention
9 juillet 2013

Bonjour, et merci pour la rapidité de votre réponse.

Je viens de faire les modifications proposées mais le problème persiste.

En fait, BrowseBprDir() et et donc BrowseBprDirDelegate(), appartiennent à la classe Public Class OSBP_MainFrm, qui est la classe de la Parent form OSBP_MainFrm.

L'appel de la méthode BrowseBprDir() se fait à partir d'une Child, ParamFrm, et donc d'une classe différente :
Public Class ParamFrm
Private Sub BprDirCmnd_Click(ByVal sender As System.Object, ByVal e As_ System.EventArgs) Handles BprDirCmnd.Click

OSBP_MainFrm.BrowseBprDir()

End Sub

Par contre, l'erreur n'apparait qu'en mode débuggage de VB.Net.
Une fois généré, lors de l'exécution de mon application ma FolderBrowserDialog apparait convenablement, sans générer d'erreur...

Je ne comprends pas.

Merci d'avance,

Thierry.
Messages postés
420
Date d'inscription
vendredi 17 novembre 2006
Statut
Membre
Dernière intervention
15 juillet 2014
6
Plusieurs cas en fonction de votre besoin:

1) Si votre méthode BrowseBprDir() n'accède à aucun membre de la classe OSBP_MainFrm, il sera déjà préférable de la déclarer Shared comme ceci:
Public Shared Sub BrowseBprDir()
End Sub

Et de l'appeler dans les enfants comme ceci :
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
    OSBP_MainFrm.BrowseBprDir()
End Sub


2) Si votre méthode BrowseBprDir() accède à des membres de la classe OSBP_MainFrm, il sera préférable de l'appeler dans les enfants comme ceci:
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
  If (Me.MdiParent IsNot Nothing) Then
      CType(Me.MdiParent, ParentFrm).BrowseBprDir()
  End If
End Sub


J'ai fait un essai avec cette example et je n'ai pas d'erreur :
Public Class ParentFrm

    Public Sub BrowseBprDir()

        Dim BrwseBpr As New FolderBrowserDialog

        BrwseBpr.RootFolder = Environment.SpecialFolder.Desktop
        BrwseBpr.Description = "Sélectionnez un répertoire"
        BrwseBpr.ShowDialog()
        If BrwseBpr.SelectedPath = String.Empty Then
            MsgBox("Pas de sélection")
        Else
            MsgBox(BrwseBpr.SelectedPath)
        End If
        BrwseBpr.Dispose()

    End Sub

    Private Sub CreateToolStripMenuItem_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles CreateToolStripMenuItem.Click
        Dim child As New ChildFrm()
        child.MdiParent = Me
        child.Show()
    End Sub

End Class

Public Class ChildFrm

    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click

        If (Me.MdiParent IsNot Nothing) Then
            CType(Me.MdiParent, ParentFrm).BrowseBprDir()
        End If

    End Sub

End Class


Si ce même exemple provoque une erreur chez vous, précisez moi votre environnement (système d'exploitation ? visual studio ? dans le cas d'un studio > à 2005 la version du framework utilisé ?)