Message non désiré avec SaveAs

Bonjour à toutes et tous,

A partir d'un classeur contenant des macros, je désire sauvegarder UNE feuille dans un répertoire donné pour un traitement ultérieur.

Un message produit par l'exécution de ma macro m'incite à penser que mon code n'est pas pertinent.

Comment l'éviter ?

Faut-il utiliser un paramètre spécifique ( notamment FileFormat) ?

Le message est le suivant :

screenshot 37

Et le code de ma macro :

Sub SauvegardeAnnuaire()
    Application.ScreenUpdating = False    
    Chemin = Range("RépertoireAnnuaire")
    If Dir(Chemin, vbDirectory) = "" Then MkDir Répertoire
    P_ref = "Ref " & Format(Range("OCI"), "##-##-####")
    P_Date = " Date " & Format(Range("Choix_DateAudit"), "yyyy-mm-dd")
    P_Nom = " Nom " & Range("NomClient")
    Nom_f = P_ref & P_Date & P_Nom & ".xlsx"

    Feuil14.Copy
    Range([A1], ActiveSheet.UsedRange).Copy
    ActiveSheet.[A1].PasteSpecial Paste:=xlPasteValues

    ' Faut-il utiliser un paramètre spécifique ( notamment FileFormat) ?

    ActiveWorkbook.SaveAs Filename:=Chemin & "\" & Nom_f
    ActiveWorkbook.Close
End Sub

Je vous remercie par avance !

Bonjour.

L'extension xslX ne supporte pas les macros.

Il suffit de faire deux choses :

Soit vous ne voulez pas de macro dur l'enregistrement, alors il duffit de mettre un Application.DisplayAlerte = False avant l'enregistrement, puis fe le remettre à True à l'issue.

Soit vous modifiez l'extension en xslM, avec un M comme macro.

@ bientôt

LouReeD

Bonjour LouReed et merci !

Ne désirant pas interdire l'affichage d'éventuels messages d'erreur, j'ai opté pour votre deuxième proposition.

Hélas, après avoir modifié l'extension en ".xlsm", non seulement le message d'avertissement initial apparait toujours mais ensuite j'en ai un nouveau !

screenshot 37

Damned !

FileFormat:=51 à la suite de la ligne SaveAs

@ bientôt

LouReeD

Edit : j'ai oublié de dire que je repartais du fichier d'origine donc avec l'extension xslx !

Mon code modifié :

Sub SauvegardeAnnuaire()
    Application.ScreenUpdating = False
    Chemin = Range("RépertoireAnnuaire")
    If Dir(Chemin, vbDirectory) = "" Then MkDir Répertoire
    P_ref = "Ref " & Format(Range("OCI"), "##-##-####")
    P_Date = " Date " & Format(Range("Choix_DateAudit"), "yyyy-mm-dd")
    P_Nom = " Nom " & Range("NomClient")
    Nom_f = P_ref & P_Date & P_Nom & ".xlsm"

    Feuil14.Copy
    Range([A1], ActiveSheet.UsedRange).Copy
    ActiveSheet.[A1].PasteSpecial Paste:=xlPasteValues

    ' Faut-il utiliser un paramètre spécifique ( notamment FileFormat) ?

    ActiveWorkbook.SaveAs Filename:=Chemin & "\" & Nom_f, FileFormat:=51
    ActiveWorkbook.Close
End Sub

Les deux messages apparaissent toujours !!!

Bonjour à tous,

Ici, tu trouveras les valeurs possibles du paramètre fileformat :https://docs.microsoft.com/fr-fr/office/vba/api/excel.xlfileformat

Apparemment, 51, c'est pour un fichier xlsx. Peux-tu essayer avec :

Fileformat:=xlOpenXMLWorkbookMacroEnabled

Ou avec 51 mais en ayant l'extension ".xlsx".

Au cas où, il doit être possible de faire :

workbooks.add
thisworkbook.Feuil14.cells.copy
activeworkbook.activesheet.cells.pastespecial paste:=xlpastevalues
activeworkbook.saveas chemin, 51 'xlsx

On copie les valeurs, on exporte pas les éventuelles codes liés...

Cdlt,

Bonjour 3GB !

A priori, Fileformat réglé sur 51 avec une extension xlsx produit toujours les mêmes messages !

Par contre l'option Fileformat réglée sur xlOpenXMLWorkbookMacroEnabled avec une extension xlsm ne génère aucune fenêtre !

Sauvegarder un fichier en "xlsm" ne contenant aucune macro me chiffonne un tantinet mais c'est tout de même une belle avancée !

Sauf, idée géniale de dernière minute, je vais donc retenir votre contribution.

Mille mercis à vous.

Vérifie quand même car je pense que si le message apparait, c'est parce que le fichier contient des macros (macros sur la feuille exportée probablement). C'est pour ça que je proposais l'alternative avec création de classeur et copie en valeur des cellules pour ne pas garder les macros de la Feuil14... Mais ça reste à confirmer.

Le fichier crée avec l'extension "xlsm" et le paramètre FileFormat:=xlOpenXMLWorkbookMacroEnabled ne comporte aucune macro !

C'est étrange d'être obligé d'affecter une extension "xlsm" à un fichier vide de macro........

Par ailleurs la proposition de création de classeur et copie en valeur des cellules se solde par un message d'erreur :

screenshot 37 01

Bonjour,

Ci dessous un code simplifié, il faudra ajuster le chemin, le nom du fichier, pour l'extension et le type de format, pour enlever le VBA c'est la paire qu'il faut xlsX et 51

On copie la feuille active du classeur source, ce qui crée automatiquement un nouveau classeur avec une seule feuille, on copie colle les valeurs afin de supprimer les formules et les liens externes, et on enregistre le classeur ainsi créé en ayant supprimer les alertes.

Le code :

Sub LouReeD()
    ' la feuille est copiée et cela crée automatiquement un nouveau classeur avec pour seule feuille celle-ci
    ' ce nouveau classeur est automatiquement "Actif"
    ActiveSheet.Copy
    ' on transforme les cellules en copie valeur
    ActiveSheet.Cells.Copy
    ActiveSheet.Range("A1").PasteSpecial Paste:=xlPasteValues
    ' on masque les alertes
    Application.DisplayAlerts = False ' arrêt des alertes d'Excel afin que cela soit "transparent" pour l'utilisateur
        ' on sauvegarde le nouveau classeur au "Chemin" avec le nom "Fichier" et "l'extension" et le type de format
        ActiveWorkbook.SaveAs ActiveWorkbook.Path & "LouReeD test" & ".xlsx", FileFormat:=51
        ' on ferme ce classeur, sans enregistrer les modifications car c'est déjà fait
        ActiveWorkbook.Close SaveChanges:=False
    Application.DisplayAlerts = True ' remise en route des alertes d'Excel
End Sub

@ bientôt

LouReeD

Re,

En fait, il ne contient peut-être pas de macros locales mais il peut contenir des objets (boutons par exemple), exportés eux aussi lors de la copie, liés à des macros externes...

Je pense que le précédent code marche mais voici un dernier essai :

ActiveSheet.cells.PasteSpecial Paste:=xlPasteFormulas
ActiveSheet.cells.PasteSpecial Paste:=xlPasteFormats

si on ne veut pas que les valeurs, à moins qu'il y ait un risque de créer des liaisons indésirables...

Le bug est lié à un codename inexistant sur le classeur exécutant. Il faut remplacer ce codename Feuil14 par un codename qui existe ou sheets("nomfeuille" ou sheets(indexfeuille).

Cdlt,

C'est pourquoi avec mon code il n'y a pas ce genre d'erreur car c'est ActiveWorkbook qui est utilisé comme ActiveSheet, du coup il n'y a pas d'erreur de nom de feuille ou de CodeName car non utilisé, il faut juste lancer le code en ayant activé la feuille dont on veut faire la sauvegarde.

Et pourquoi faire un WorkBooks.Add alors que le fait de faire une copy de feuille le fait automatiquement ?

@ bientôt

LouReeD

Comme je l'ai dit sur mon précédent commentaire, si la feuille copiée contient un objet auquel on a affecté une macro, l'objet est copié avec sheets.copy et la macro est toujours active (en tant que macro "externe"). Moi non plus, je ne comprenais pas alors j'ai fait un essai car je ne voyais pas d'autres raisons d'avoir une demande de confirmation d'enregistrement au format xlsx.

Donc avec ta méthode, il faudrait rajouter ensuite quelque chose comme une boucle sur toutes les formes et oleobjects de la feuille pour les supprimer... Enfin si mon intuition est bonne.

D'où l'ajout d'un classeur et la copie en formules et formats (ou en valeurs) des cellules.

Et je crois que pour l'enregistrement il faut demander le path du classeur exécutant (d'origine) car c'est le nouveau qui est devenu actif et qui, avant la sauvegarde, n'a pas d'emplacement :

ActiveWorkbook.SaveAs thisworkbook.Path & "LouReeD test" & ".xlsx", FileFormat:=51

A bientôt,

Bonsoir,

Ok je n'avais pas saisi le fait du lien d'une forme sur un code VBA.

Pour ce qui est du chemin, par défaut chez moi cela va dans "mes documents", mais c'est pourquoi j'avais indiqué qu'il fallait adapter le chemin et le nom du fichier.
Le code modifié suite à vos remarques (je progresse ! ) :

Sub LouReeD()
    Application.ScreenUpdating = False
    Dim Chemin As String ' variable qui représente le chemin pour accèder au dossier d'enregistrement du fichier
    Dim Fichier As String ' variable qui contiendra le nom du fichier lors de la boucle
    Dim Sh As Shape ' variable qui permettra de tourner sur les shapes
    Chemin = ThisWorkbook.Path
    Fichier = "\LouReeD"
    ' la feuille que l'on vient de créer est copiée et cela crée automatiquement un nouveau classeur avec pour seule feuille celle-ci
    ' ce nouveau classeur est automatiquement "Actif"
    ActiveSheet.Copy
    Application.DisplayAlerts = False ' arrêt des alertes d'Excel afin que cela soit "transparent" pour l'utilisateur
        With ActiveSheet
            .Cells.Copy
            .Range("A1").PasteSpecial Paste:=xlPasteValues
            .Range("A1").Select
        End With
        Application.CutCopyMode = False
        ' on efface les shapes qui contiennent peut-être des lien vers des macros
        For Each Sh In ActiveSheet.Shapes
            Sh.Delete
        Next Sh
        ' on sauvegarde le nouveau classeur au "Chemin" avec le nom "Fichier" et "l'extension" trouvée
        ActiveWorkbook.SaveAs Chemin & "\LouReeD test" & ".xlsx", FileFormat:=51
        ' on ferme ce classeur, sans enregistrer les modifications car c'est déjà fait
        ActiveWorkbook.Close SaveChanges:=False
    Application.DisplayAlerts = True ' remise en route des alertes d'Excel
End Sub

Ce n'est que pour moi, car le sujet est déjà résolu !

@ bientôt

LouReeD

Re LouReed,

Dans ce cas, je me prête au jeu avec une boucle sur les oleobjects et une condition pour ne supprimer que les formes contenant une macro. J'essaie en utilisant directement la méthode close mais ce n'est pas sûr que ça marche sans ce message. D'ailleurs, je crois que mettre le paramètre savechanges sur true permet d'éviter d'avoir un message de demande de confirmation (enfin, je ne sais pas trop quand est-ce que ce message survient) :

Sub LouReeD()

Chemin = ThisWorkbook.Path & "\LouReeD DeRoule.xlsx" 'petit anagramme au passage :)
sheets("name").Copy

With activeworkbook
    with .activesheet
        For Each Sh In .Shapes
            if Sh.onaction <> "" then Sh.Delete
        Next Sh
        for each oleo in .oleobjects
            oleo.delete
        next oleo
    End With
    '.SaveAs Chemin, 51 'xlOpenXMLWorkbook
    .Close true, chemin
end with

End Sub

MAIS le problème, c'est que si jamais il y a une macro évènementielle sur la feuille et bien elle est exportée elle aussi. Donc je pense qu'il vaut mieux copier les valeurs ou formules des cellules plutôt que la feuille car là, il faudrait ajouter une référence pour manipuler le VBProjects et supprimer le code par macro ...

Cdlt,

Non Non, sur mon fichier ici, l'événementiel est supprimé également, d'ailleurs tout ce qui est VBA est supprimé, seul la référence de code VBA reste sur les shapes...

Qu'est ce que le oleobjet ?

@ bientôt

LouReeD

Les oleobjects, ce sont les contrôles activeX. Peut-être que la collection regroupe d'autres objets mais si c'est le cas, je n'en ai pas connaissance...

Ah bon, le code de la feuille copiée est supprimé ? Etrange...

Re-Edit : je viens de tester après fermeture du classeur et désactivation des alertes et effectivement, le code disparait !

Il est supprimé suite à l'enregistrement et non pas suite à la copie...

Perso, j'évite les ActiveX, sauf pour la détection du survole de souris... Je trouve que c'est plus lourds que les simples formes, mais ce n'est peut être qu'une impression... En plus avec Mac ça passe mal...

@ bientôt

LouReeD

Oui, je viens d'essayer. En fait, j'ai l'impression qu'il faut bien fermer le classeur (donc en mode sans macros) pour que toute macro disparaisse.

Oui, moi non plus, je n'y touche pas... J'avais un mac avant et je n'arrivais pas à ouvrir les fichiers qui en contenaient. Sauf cas assez rares, je pense qu'on peut s'en passer.

Cdlt,

Bonjour LouReed et 3GB, Bonjour le Forum !

Merci, merci et merci ! Vraiment.

Vos apports et échanges me permettent d'avancer dans mon projet et d'améliorer mes compétences excelliennes.......

Pour votre information, j'essaie d'automatiser le plus possible la production de rapports de notre service "Certification". Les auditeurs concernés utilisent Excel pour saisir et éditer différents type de rapports.

Mon souhait est d'améliorer l'existant et surtout de collecter des informations disséminées dans les différentes feuilles du classeur, ces informations devant être ultérieurement agrégées dans un annuaire destiné à être communiqué aux Ministères concernés.

Ma ligne directrice actuelle est de mettre en place, dans le classeur "Modèle rapport", une feuille (Feuil14) chargée de collecter les informations nécessaires. Cette feuille ne contient QUE des valeurs textes et des valeurs (via des formules). L'auditeur lancera une macro, cette dernière qui fait l'objet de nos échanges, fait une copie, en valeur; de cette feuille dans un répertoire dédié pour un traitement ultérieur via Power Query.

A ce propos, au lieu d'envisager un fichier "xlsm" ou "xlsx", je pense plutôt m'atteler à la création d'un fichier CSV. Que me conseillez-vous comme paramètre XFileFormat ? Quel est celui qui vous semble le plus pertinent (xlCSV, xlCSVMSDOS, xlCSVUTF8, xlCSVWindows)

Rechercher des sujets similaires à "message desire saveas"