IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Excel Discussion :

Fonction incompatible avec le verrouilage des feuilles ?


Sujet :

Excel

  1. #1
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2015
    Messages
    26
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mai 2015
    Messages : 26
    Points : 12
    Points
    12
    Par défaut Fonction incompatible avec le verrouilage des feuilles ?
    Bonjour,

    Dans des macros, j'utilise les propriétés DataBodyRange.Delete et ListRow.Index. Tout fonctionne très bien jusqu'à ce que j'active la protection de ma feuille. A ce moment là, mes macro plantent sur les 2 fonctions citées. Tout les cellules de la table sur laquelle j’agis sont bien déverrouillées ; j'ai essayé de multiples combinaisons de configurations des options de verrouillage, sans succès.
    Je précise bien : mes macros fonctionnent correctement sans la protection de la feuille et les zones d'actions sont déverrouillées.

    - Pour DataBodyRange.Delete, l'erreur indiquée est "Erreur d'exécution 1004 : La méthode Delete de la classe Range a échoué"
    Mes recherches semblent m'indiquer que cette méthode est incompatible avec le verrouillage d'une feuille et que la solution est de déverrouiller la feuille de calcul avant d'effectuer l'opération et de la reverrouiller après. Cela m'étonne.
    Est-ce que quelqu'un connaitrait déjà ce problème et pourrait me confirmer cela ou m'indiquer une autre possibilité ?

    - Pour ListRow.Index, l'erreur donnée est "Erreur d'exécution 1004 : Erreur définie par l'application ou par l'objet"
    Je n'ai pas trouvé d'info sur cette fonction et ce problème, est-ce que la raison et la solution pourraient être les mêmes qu'au-dessus ?

    Merci d'avance

  2. #2
    Membre expérimenté
    Avatar de tototiti2008
    Homme Profil pro
    Formateur/développeur
    Inscrit en
    Octobre 2008
    Messages
    747
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Formateur/développeur

    Informations forums :
    Inscription : Octobre 2008
    Messages : 747
    Points : 1 332
    Points
    1 332
    Par défaut
    Bonjour pico,

    Tu peux protéger une feuille de façon à ce que les utilisateurs ne puissent pas la modifier mais le code VBA le pourra
    Va voir l'aide sur la méthode Worksheet.Protect, en mettant UserInterfaceOnly à True ça devrait améliorer les choses.
    ça nécessite de protéger la feuille par du code, pas manuellement
    Pour la 1ère erreur, oui protéger la feuille t'empêche de supprimer les cellules a priori
    Pour la 2ème, je ne sais pas ce qu'est ListRow, donc je ne peux pas répondre

  3. #3
    Membre actif Avatar de Denis la Malice
    Homme Profil pro
    FabManager
    Inscrit en
    Février 2013
    Messages
    133
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 65
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : FabManager
    Secteur : Services de proximité

    Informations forums :
    Inscription : Février 2013
    Messages : 133
    Points : 287
    Points
    287
    Par défaut Réponse à la première question
    Au lieu de :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Sheets(1).ListObjects(1).DataBodyRange.delete
    Essaie :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Sheets(1).ListObjects(1).DataBodyRange = ""
    Sans toucher à la protection de ton tableau.
    De la réflexion, naît l'action ...

  4. #4
    Membre actif Avatar de Denis la Malice
    Homme Profil pro
    FabManager
    Inscrit en
    Février 2013
    Messages
    133
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 65
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : FabManager
    Secteur : Services de proximité

    Informations forums :
    Inscription : Février 2013
    Messages : 133
    Points : 287
    Points
    287
    Par défaut Précisions pour la deuxième question
    Bonjour Pico142,

    Comment utilises-tu la propriété Listrow.Index ? Ne pratiquant que très peu la divination, j'ai du mal à t'aider sur ce coup-là. En revanche, j'utilise fréquemment les Listobjects et la protection des feuilles.

    Cordialement.
    De la réflexion, naît l'action ...

  5. #5
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2015
    Messages
    26
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mai 2015
    Messages : 26
    Points : 12
    Points
    12
    Par défaut
    Citation Envoyé par tototiti2008 Voir le message
    Tu peux protéger une feuille de façon à ce que les utilisateurs ne puissent pas la modifier mais le code VBA le pourra
    Va voir l'aide sur la méthode Worksheet.Protect, en mettant UserInterfaceOnly à True ça devrait améliorer les choses.
    Je verrouille également l'accès au projet VBA de sorte que l'utilisateur lambda ne pourra pas aller y toucher. Ainsi, je maitrise totalement ce que les utilisateur peuvent toucher.
    Je ne connais pas le méthode Worksheet.Protect, je vais regarder cela de plus près, voir ce que ça peut m'apporter.

    Citation Envoyé par Denis la Malice Voir le message
    Essaie :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Sheets(1).ListObjects(1).DataBodyRange = ""
    La fonction en elle-même fonctionne, mais elle ne me convient pas spécialement. La fonction delete supprime bien toutes les lignes du tableau, ta fonction "rempli le tableau avec du vide". Si je ne trouve pas de solution faisant vraiment ce que je voulais, celle-ci peut faire l'affaire, mais je voudrais que le tableau soit remis à neuf et pas seulement les données effacées.
    Le problème est le suivant avec ta méthode : je vais charger un ensemble de données dans mon tableau, puis vider le tableau, puis charger un autre ensemble de données ... Si le 2nd ensemble contient plus de données que le premier, le tableau s’agrandira pour s'adapter. En revanche, si le 2nd ensemble contient moins de données que le premier, il va rester des lignes vides au fond du tableau, c'est ce que je voudrais éviter.

    Citation Envoyé par Denis la Malice Voir le message
    Comment utilises-tu la propriété Listrow.Index ? Ne pratiquant que très peu la divination, j'ai du mal à t'aider sur ce coup-là. En revanche, j'utilise fréquemment les Listobjects et la protection des feuilles.
    C'est dommage pour le divination, ça serait bien souvent utile
    Je viens de me rendre compte que cette ligne n'est pas la source du problème. J'utilise Index pour avoir des infos sur la ligne que je viens de rajouter au tableau de la façon suivante.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    Dim LR As ListRow
    Set LR = Range("Tab_Init").ListObject.ListRows.Add
    Dim LRIndex As Integer
    LRIndex = LR.Index
    Si le code n'est pas protégé, au passage de la seconde ligne, une nouvelle ligne vide est ajoutée dans mon tableau. Si le code est protégé, cette ligne ne s'ajoute pas, ainsi LR n'est pas attribué et la fonction index ne fonctionne pas (logique ^^).
    Enlever la protection de la ligne situé directement sous le tableau ne change rien au problème.

  6. #6
    Membre actif Avatar de Denis la Malice
    Homme Profil pro
    FabManager
    Inscrit en
    Février 2013
    Messages
    133
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 65
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : FabManager
    Secteur : Services de proximité

    Informations forums :
    Inscription : Février 2013
    Messages : 133
    Points : 287
    Points
    287
    Par défaut Listobject et protection de feuille
    Bonjour,
    Tu ne peux pas redimensionner un tableau de type Listobject si la feuille est protégée. même si toutes les cellules sont déverrouillées et même avec l'option UserInterfaceOnly.

    Soit tu enlèves la protection dans ta macro, juste avant d'ajouter une ligne, puis tu remets la protection juste après.

    Soit tu gardes un tableau de taille fixe et, par exemple, tu masques les lignes vides.

    Les Listobjects sont très pratiques, mais c'est la galère avec la protection des feuilles, surtout si on veut mettre un mot de passe sur chaque feuille. Il apparait alors dans le code et il faut ajouter un mot de passe sur le projet. Sachant qu'il n'est pas très difficile de casser un mot de passe Office.

    Cordialement.
    De la réflexion, naît l'action ...

  7. #7
    Membre expérimenté
    Avatar de tototiti2008
    Homme Profil pro
    Formateur/développeur
    Inscrit en
    Octobre 2008
    Messages
    747
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Formateur/développeur

    Informations forums :
    Inscription : Octobre 2008
    Messages : 747
    Points : 1 332
    Points
    1 332
    Par défaut
    Bonsoir,

    Tu ne peux pas redimensionner un tableau de type Listobject si la feuille est protégée. même si toutes les cellules sont déverrouillées et même avec l'option UserInterfaceOnly.
    Oui, Denis a raison, ça a l'air galère, les ListObjects sont un cas à part encore une fois

  8. #8
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2015
    Messages
    26
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mai 2015
    Messages : 26
    Points : 12
    Points
    12
    Par défaut
    Bonjour,

    Ça me fait bien ch*** tout ça, mais au moins ça a le mérite d'être clair.
    Je ne sais pas encore pour quelle solution, je vais opter.

    Merci a tous pour vos éclaircissements.

  9. #9
    Membre actif Avatar de lionel86500
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2013
    Messages
    144
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Vienne (Poitou Charente)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2013
    Messages : 144
    Points : 214
    Points
    214
    Par défaut
    Bonjour,

    Moi quand je prépare un travail pour des utilisateurs, je ne sais jamais ce qu'il pourront faire comme erreur.
    Alors je prends pour principe de verrouiller les feuilles.
    Lors d'un traitement d'une macro je déverrouille via la macro, je fais le traitement et je verrouille via la macro.
    Pour info je met un mot de passe sur le verrou.
    Lionel

  10. #10
    Membre actif Avatar de Denis la Malice
    Homme Profil pro
    FabManager
    Inscrit en
    Février 2013
    Messages
    133
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 65
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : FabManager
    Secteur : Services de proximité

    Informations forums :
    Inscription : Février 2013
    Messages : 133
    Points : 287
    Points
    287
    Par défaut Une solution sans enlever la protection de la feuille !
    Bonjour,

    voici un morceau de code qui fonctionne. Au départ, j'ai un tableau d'au moins 2 colonnes. Toutes mes cellules ont la propriété "verrouillée".

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    Sub essai()
         Dim LR As ListRow, Tableau As ListObject, LRIndex As Integer
         Dim i As Long
     
         Set Tableau = Sheets(1).ListObjects(1)
     
         Sheets(1).Protect UserInterfaceOnly:=True, _
              DrawingObjects:=True, _
              Contents:=True, _
              Scenarios:=True, _
              AllowFormattingCells:=False, _
              AllowFormattingColumns:=False, _
              AllowFormattingRows:=False, _
              AllowInsertingColumns:=False, _
              AllowInsertingHyperlinks:=False, _
              AllowDeletingColumns:=False, _
              AllowSorting:=False, _
              AllowFiltering:=False, _
              AllowUsingPivotTables:=False, _
              AllowDeletingRows:=False, _
              AllowInsertingRows:=False
     
     
         If Not Tableau.DataBodyRange Is Nothing Then Tableau.DataBodyRange.Delete
     
     
         For i = 1 To 5
              Set LR = Tableau.ListRows.Add
              If Tableau.DataBodyRange Is Nothing Then
                   Sheets(1).Cells(Tableau.HeaderRowRange.Row + 1, Tableau.ListColumns(1).Range.Column) = 0
              Else
                   Sheets(1).Cells(Tableau.HeaderRowRange.Row + Tableau.DataBodyRange.Rows.Count + 1, Tableau.ListColumns(1).Range.Column) = 0
              End If
              LRIndex = LR.Index
              Debug.Print "LRIndex = " & LRIndex
              ' Je remplis ma ligne
              Tableau.ListColumns(1).DataBodyRange.Cells(LRIndex, 1) = LRIndex
              Tableau.ListColumns(2).DataBodyRange.Cells(LRIndex, 1) = Chr(Asc("A") + LRIndex - 1)
         Next i
     
    End Sub
    Quand le tableau est vide, on ne peut pas utiliser les propriétés de DataBodyRange qui vaut Nothing. Donc avant d'appeler la méthode Delete de DataBodyRange, je vérifie que le tableau n'est pas déjà effacé.

    Quand j'appelle la méthode ListRows.Add, je vois bien (avec le débogueur) que LR est initialisé partiellement (il existe, mais il n'a aucune propriété, donc pas d'Index). L'astuce est d'écrire dans la nouvelle ligne créée, qui, comme par magie existe alors. Il faut trouver l'adresse d'une cellule de la nouvelle ligne, sans utiliser Index de LR. Et pour utiliser DataBodyRange.Rows.Count, il faut d'abord vérifier que DataBodyRange existe.
    Donc, si la tableau est vide (Tableau.DataBodyRange Is Nothing) alors j'écris dans la ligne qui suit l’entête si le tableau n'est pas vide, j'écris dans la ligne qui suit la dernière ligne du DataBodyRange.

    En début de procédure, je positionne la protection de la feuille. J'interdis tout, y compris l'insertion et la suppression des lignes. L'important est le paramètre "UserInterfaceOnly:=True". A n'utiliser qu'à l'ouverture du fichier, mais inutile de repositionner la protection à chaque fois (je l'ai mis dans la procédure pour faire mes jeux d'essai).

    La dernière fois que je me suis cassé les dents sur les Listobjects et les protections de feuille, j'ai renoncé trop vite.
    De la réflexion, naît l'action ...

  11. #11
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2015
    Messages
    26
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mai 2015
    Messages : 26
    Points : 12
    Points
    12
    Par défaut
    Merci pour tout ça Denis, je vais tester et essayer de bien comprendre le fonctionnement.

Discussions similaires

  1. [XL-2003] Fonction Si avec les valeurs des cellules
    Par magyaddello dans le forum Macros et VBA Excel
    Réponses: 4
    Dernier message: 19/08/2010, 13h48
  2. manipuler excel avec delphi ( gestion des feuilles)
    Par lila23 dans le forum Débuter
    Réponses: 4
    Dernier message: 01/04/2009, 15h14
  3. liste déroulante avec les noms des feuilles d'un classeur fermé
    Par winclass dans le forum Macros et VBA Excel
    Réponses: 1
    Dernier message: 18/12/2008, 22h39
  4. Fonction incompatible avec IE
    Par Sanceray3 dans le forum Général JavaScript
    Réponses: 2
    Dernier message: 23/02/2007, 10h22
  5. Comment remplir un ComboBox avec le nom des feuilles Excel ?
    Par libracom dans le forum API, COM et SDKs
    Réponses: 2
    Dernier message: 27/06/2005, 15h14

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo