Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

MartiFab

XLDnaute Nouveau
Bonjour a tous !

Cela fait déjà un petit moment que j’apprécie la qualité de ce forum et la précieuse quantité d’informations qui s’y trouve. Jusqu'à aujourd’hui j’avais réussi a résoudre mes problèmes en consultant les discussions disponibles. Voici donc ma première question :

Tout d’abord exposons le problème.
Dans le cadre de mon travail je reçois un « Classeur Source » ne contenant qu’une feuille de calcul. Je place ce fichier Excel dans un Dossier qui se situe sur mon bureau. Mon objectif est de pouvoir sélectionner une plage de cellules dans « Classeur Source » et la coller dans un « Classeur Cible » (placé dans le même dossier).
Mes difficultés pro viennent du fait que je voudrais lancer la macro effectuant cette opération depuis un troisième fichier Excel « Tableau de contrôle » lui-même situe dans le Dossier. Pour mieux comprendre :

Contenu du dossier avant exécution de la macro : Classeur Source.xlsx, Tableau de contrôle.xlsx

Ouverture de « Tableau de contrôle », exécution de la macro, nouveau contenu du dossier : Classeur Source.xlsx, Tableau de Contrôle.xlsx, Classeur Cible.xlsx (avec les données importées depuis « Classeur Source »)

Mon Code

Code:
Sub preparation()

    'Declaration des objets
    Dim awBook As Workbook
    Dim tempBook As Workbook
    Dim currentCell As Range
    
    'Declaration des variables numeriques
    Dim lRow, lCol, count, curRow, curCol As Integer
    
    'Declaration des variables chaines de caracteres
    Dim awBookPath, tempBookPath As String
    
    
    'indication du nom complet des fichiers utilises. « Classeur Source » est awFile.xlsx
    '"Classeur Cible" est tempFile
    awBookPath = "C:\Users\industrialstemp\Desktop\SaReDEX\awFile.xlsx"
    tempBookPath = "C:\Users\industrialstemp\Desktop\SaReDEX\tempFile.xlsx"
    
    'Creation du nouveau fichier excel  
    Set tempBook = Workbooks.Add
    tempBook.SaveAs (tempBookPath)
    
    Set awBook = Workbooks.Open(awBookPath)
    
    
    ‘On donne un nom aux colonnes du tableau original
    awBook.Worksheets(1).Cells(1, 1) = "Sample Code"
    awBook.Worksheets(1).Cells(1, 2) = "Site Code"
    awBook.Worksheets(1).Cells(1, 3) = "Sample Date"
    awBook.Worksheets(1).Cells(1, 4) = "Sample Analysis"
    awBook.Worksheets(1).Cells(1, 5) = "Sample Delivery"
    awBook.Worksheets(1).Cells(1, 6) = "OB"
    awBook.Worksheets(1).Cells(1, 7) = "Sample Point"
    
    'Copier/Coller des headers de colonnes  du tableau original pour les decaler vers le
    'haut
    awBook.Worksheets(1).Range(Cells(2, 8), Cells(2, 8).End(xlToRight)).Copy Destination:=awBook.Worksheets(1).Cells(1, 8)
    awBook.Worksheets(1).Rows(2).Delete
    
    'Donne les dimensions du tableau original modifie (nombre de lignes et colonnes)
    lRow = awBook.Worksheets(1).Cells(Rows.count, 1).End(xlUp).Offset(1, 0).Row - 1
    lCol = awBook.Worksheets(1).Cells(1, Columns.count).End(xlToLeft).Offset(1, 0).Column

   
 count = 2
    For Each currentCell In awBook.Worksheets(1).Range(Cells(2, 8), Cells(lRow, lCol))
        If Not IsEmpty(currentCell) Then
            curRow = currentCell.Row
            curCol = currentCell.Column
                        
            'Copie une plage dans le tableau de la feuille 1 du Classeur Source et la 
            'colle dans le  Classeur Cible
            'PROBLEME SURVIENT A LA LIGNE SUIVANTE *!*!*!*!*!*!*!*!*!*!*!*!
            awBook.Worksheets(1).Range(Cells(curRow, 1), Cells(currRow, 7)).Copy Destination:=tempBook.Worksheets(1).Cells(count, 1)

            'import in the temporary file the determinant and its value and add it following previous copied data
            tempBook.Worksheets(1).Cells(count, 8) = awBook.Worksheets(1).Cells(1, curCol)
            tempBook.Worksheets(1).Cells(count, 9) = currentCell

            'incrementation of the row counter in table in temporary file
            count = count + 1
        End If
    Next currentCell

    'We give a name to the headers of the temporary file
    tempBook.Worksheets(1).Cells(1, 1) = "Sample Code"
    tempBook.Worksheets(1).Cells(1, 2) = "Site Code"
    tempBook.Worksheets(1).Cells(1, 3) = "Sample Date"
    tempBook.Worksheets(1).Cells(1, 4) = "Sample Analysis"
    tempBook.Worksheets(1).Cells(1, 5) = "Sample Delivery"
    tempBook.Worksheets(1).Cells(1, 6) = "OB"
    tempBook.Worksheets(1).Cells(1, 7) = "Sampling Point"
    tempBook.Worksheets(1).Cells(1, 8) = "Determinant"
    tempBook.Worksheets(1).Cells(1, 9) = "Result"

End Sub

Comme je le souligne dans le code, mon instruction pour copier les cellules du Classeur Source et les coller vers mon Classeur Cible fait bugger la macro. Je crois comprendre que mon problème vient de la déclaration de mes objets. Il y a probablement besoin de pouvoir ouvrir le Classeur Source et le Classeur Cible simultanément. J’ai trouvé sur internet beaucoup de solutions, notamment l’utilisation de ThisWorkBook, cependant dans mon cas cela n’est pas possible étant donné que la macro est lancée depuis un fichier indépendant des deux qui nous intéressent. Du moins c’est ce que j’ai compris.

Ma question est donc la suivante :
Tout d’abord est-il possible de faire ce que je souhaite, a savoir lancer la macro depuis un classeur et faire agir la macro sur deux autres classeurs ? Dans mon code qu’est ce qui semble loucher ?

Je joins un exemple de awFile.xlsx a ce message.

Je vous remercie si vous passez par là et avez une réponse à m’apporter. J’espère que cette discussion servira à d’autres dans le même cas.

Merci a tous ! A bientôt
 

Pièces jointes

  • awFile.xlsx
    9.6 KB · Affichages: 51

Pierrot93

XLDnaute Barbatruc
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Bonjour,

essaye comme ceci, non testé..
Code:
With awBook.Worksheets(1)
    .Range(.Cells(curRow, 1), .Cells(currRow, 7)).Copy Destination:=tempBook.Worksheets(1).Cells(Count, 1)
End With
bon après midi
@+
 

MartiFab

XLDnaute Nouveau
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Bonjour Pierrot,

Merci pour ta reponse si rapide. Je viens de tester ton code, malheureusement cela ne fonctionne pas. Penses-tu que l'erreur soit liee avec la declaration de mes objets awBook et tempBook ?

Merci Encore
Bon apres-midi
 

Pierrot93

XLDnaute Barbatruc
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Re,

Penses-tu que l'erreur soit liee avec la declaration de mes objets awBook et tempBook ?
non, doivent bien être de type "workbook" et les 2 classeurs être ouverts, ce qui sempble être le cas...
tu as bien mis le "range" ..... copy et destination:=... sur la même ligne ??
 

MartiFab

XLDnaute Nouveau
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Pierrot !

Je viens de trouver ! Je n'arrive pas a croire que l'erreur etait aussi stupide... Tu vas rire, cela fait deux jours que je bute dessus. Il a y a un r en trop dans currCol, ma variable est curCol... Je me sens ridicule d'un coup. Poster sur le forum pour ca... Bref cela pourra peut etre aider quelqu'un.

Je te remercie en tous les cas pour ta rapidite et ta reponse. C'est tres sympa.

A bientot pour un probleme moins stupide j'espere !

Bon apres midi
 

Pierrot93

XLDnaute Barbatruc
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Re,

attention, tu as "curRow" et "currRow" (avec 2r), une seule variable semble déclarée et initialisée... d'ou l'interêt de placer l'instruction "Option Explicit" en tête de module, te permet de déceler tout de suite ce type d'erreur...
 

MartiFab

XLDnaute Nouveau
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Merci Pierrot,

Meme conclusion. Je vais me renseigner sur l'instruction "Option Explicit", je ne la connais pas. Desole de t'avoir fait perdre ton temps pour une chose aussi triviale. Penses-tu que je doive supprimer cette discussion qui s'avere pas tres utile du coup :) ?
 

Pierrot93

XLDnaute Barbatruc
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Re,

ton code ci-dessous présentait tout de même une anomalie...
Code:
awBook.Worksheets(1).Range(Cells(curRow, 1), Cells(currRow, 7)).Copy
en l'état, sans présition de la feuille et ou du classeur, la propriété "cells" s'appliquait aux objets actifs (feuille classeur), pas forcement donc sur les objets voulus.....
 

Gorfael

XLDnaute Barbatruc
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Salut MartiFab, Pierrot93 et le forum
Bienvenue
Au moins un qui donne des données intéressantes et complètes.

Juste quelques remarques :
Code:
'Declaration des variables numeriques
    Dim lRow, lCol, count, curRow, curCol As Integer
Sans être sûr à 100% (je n'ai que la version 2003), tu déclares curCol en Integer, toutes les autres en Variant. Si tu ne met pas le type (ou le caractère du type), Excel ne comprend pas.
La vrai syntaxe est, par exemple :
Code:
'Declaration des variables chaines de caracteres
    Dim awBookPath as String, tempBookPath As String
Nota : Tu déclares une variable de nom "count" : pas une riche idée d'utiliser des mots réservés (qu'utilise Excel) comme nom de variable
Code:
'Copier/Coller des headers de colonnes  du tableau original pour les decaler vers le
    'haut
    awBook.Worksheets(1).Range(Cells(2, 8), Cells(2, 8).End(xlToRight)).Copy Destination:=awBook.Worksheets(1).Cells(1, 8)
ce que tu as écrit :
Code:
'Copier/Coller des headers de colonnes  du tableau original pour les decaler vers le
     'haut
     awBook.Worksheets(1).Range(ActiveWorkbook.ActiveSheet.Cells(2, 8), ActiveWorkbook.ActiveSheet.Cells(2,  8).End(xlToRight)).Copy Destination:=awBook.Worksheets(1).Cells(1,  8)
Quand tu ne précises pas le classeur ou la feuille, Excel prend celui actif par défaut. Comme Pierrot93 a déjà corrigé...
Penser à corriger les autres de même type, comme
Code:
     For Each currentCell In awBook.Worksheets(1).Range(Cells(2, 8), Cells(lRow, lCol))
ou
Code:
awBook.Worksheets(1).Range(Cells(curRow, 1), Cells(currRow, 7)).Copy Destination:=tempBook.Worksheets(1).Cells(count, 1)
Ce n'est pas parce que ta feuille active est celle d'index 1 d'awBook qu'il faut laisser les erreurs : ne pas oublier la Loi de Murphy...
Code:
'We give a name to the headers of the temporary file
    tempBook.Worksheets(1).Cells(1, 1) = "Sample Code"
    tempBook.Worksheets(1).Cells(1, 2) = "Site Code"
    tempBook.Worksheets(1).Cells(1, 3) = "Sample Date"
    tempBook.Worksheets(1).Cells(1, 4) = "Sample Analysis"
    tempBook.Worksheets(1).Cells(1, 5) = "Sample Delivery"
    tempBook.Worksheets(1).Cells(1, 6) = "OB"
    tempBook.Worksheets(1).Cells(1, 7) = "Sampling Point"
    tempBook.Worksheets(1).Cells(1, 8) = "Determinant"
    tempBook.Worksheets(1).Cells(1, 9) = "Result"
Euh... si j'ai bien suivi, tu as fait les mêmes définitions pour l'autre classeur en début => plus simple de copier la première ligne (entière, ou de A à I)

Excel fait toujours ce qu'on lui demande de faire, et quelques (rares) fois ce qu'on veut qu'il fasse :p
A+
 

MartiFab

XLDnaute Nouveau
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Bonjour Gorfael,

Merci pour ta reponse. Toutes ces precisions sont tres interessantes et enrichissantes pour moi. Je vais appliquer ces quelques conseils. C'est la premiere fois que je pose une question sur un forum quel qu'il soit et je suis ravi du resultat. Je n'hesiterai plus a l'avenir.

Merci encore a vous deux, Gorfael et Pierrot
 

MartiFab

XLDnaute Nouveau
Re : Copie de donnees d'un ClasseurA vers un Classeur B par une macro dans Classeur C

Bonjour à tous !

Suite à la question que j’ai posée hier, je poste mon code corrigé en suivant les bons conseils de Pierrot93 et Gorfael. N’hésitez pas à me faire par de vos remarques si vous voyez des choses fausses ou à améliorer. J’espère également que cela pourra en aider certains.

Bonne journée à tous :)

code corrigé

Code:
Sub preparation()
    
    'Declaration des objets
    Dim awBook As Workbook
    Dim tempBook As Workbook
    Dim currentCell As Range
    
    'Declaration des variables numeriques
    Dim lRow As Integer
    Dim lCol As Integer
    Dim counter As Integer
    Dim curRow As Integer
    Dim curCol As Integer
               
     
    'Declaration of the string variables
    Dim awBookPath As String            'Classeur Source
    Dim tempBookPath As String         'Classeur Cible
        
    'Nom entier des noms de fichiers a utiliser
    awBookPath = "C:\Users\industrialstemp\Desktop\SaReDEX\awFile.xlsx"
    tempBookPath = "C:\Users\industrialstemp\Desktop\SaReDEX\tempFile.xlsx"
    
    'On cree le classeur cible 
    Set tempBook = Workbooks.Add
    tempBook.SaveAs (tempBookPath)
    'on ouvre le classeur source
    Set awBook = Workbooks.Open(awBookPath)
    
    'On donne un nom aux headers de la table de la feuil1 du Classeur Source
    awBook.Worksheets(1).Cells(1, 1) = "Sample Code"
    awBook.Worksheets(1).Cells(1, 2) = "Site Code"
    awBook.Worksheets(1).Cells(1, 3) = "Sample Date"
    awBook.Worksheets(1).Cells(1, 4) = "Sample Analysis"
    awBook.Worksheets(1).Cells(1, 5) = "Sample Delivery"
    awBook.Worksheets(1).Cells(1, 6) = "OB"
    awBook.Worksheets(1).Cells(1, 7) = "Sample Point"
    
    'On copie/colle ces headers pour les deplacer d’une ligne vers le haut dans le 
    'Classeur Source 
    'On supprime ensuite la ligne 2 qui se retrouve vide
    awBook.Worksheets(1).Range(ActiveWorkbook.ActiveSheet.Cells(2, 8), ActiveWorkbook.ActiveSheet.Cells(2, 8).End(xlToRight)).Copy Destination:=awBook.Worksheets(1).Cells(1, 8)
    awBook.Worksheets(1).Rows(2).Delete
    
    'Donne le nbre de lignes et colonnes de la table dans Classeur Source une fois remaniee
    lRow = awBook.Worksheets(1).Cells(Rows.Count, 1).End(xlUp).Offset(1, 0).Row - 1
    lCol = awBook.Worksheets(1).Cells(1, Columns.Count).End(xlToLeft).Offset(1, 0).Column
    
    'C'est dans ce qui suit que l'on va copier des donnees depuis le Classeur Source
    'et les coller dans le Classeur Cible
        counter = 2
        For Each currentCell In awBook.Worksheets(1).Range(Cells(2, 8), Cells(lRow, lCol))
            If Not IsEmpty(currentCell) Then
                curRow = currentCell.Row
                curCol = currentCell.Column
                
                awBook.Worksheets(1).Range(ActiveWorkbook.ActiveSheet.Cells(curRow, 1), ActiveWorkbook.ActiveSheet.Cells(curRow, 7)).Copy _
                    Destination:=tempBook.Worksheets(1).Cells(counter, 1)

'on peut ici egalement appliqué le code suivant qui fera la meme actions que la 
'la ligne ci-desus  
'With awBook.Worksheets(1)
'    .Range(.Cells(curRow, 1), .Cells(curRow, 7)).Copy 'Destination:=tempBook.Worksheets(1).Cells(Count, 1)
'End With
                    
                tempBook.Worksheets(1).Cells(counter, 8) = awBook.Worksheets(1).Cells(1, curCol)
                tempBook.Worksheets(1).Cells(counter, 9) = currentCell
                
                counter = counter + 1
            End If
        Next currentCell
        
    'On donne un nom aux headers de la table dans Classeur Cible, les 7 premiers 
    ' Sont identiques a ceux de la table dans le Classeur Source
    awBook.Worksheets(1).Range(ActiveWorkbook.ActiveSheet.Cells(1, 1), ActiveWorkbook.ActiveSheet.Cells(1, 7)).Copy _
            Destination:=tempBook.Worksheets(1).Cells(1, 1)
    tempBook.Worksheets(1).Cells(1, 8) = "Determinant"
    tempBook.Worksheets(1).Cells(1, 9) = "Result"

    'On enregistre les modifications dans le Classeur Cible
    tempBook.Save

    'On ferme le classeur source sans sauvegarder les modifications apportees
    awBook.Close False

End Sub
 

Membres actuellement en ligne

Statistiques des forums

Discussions
286 547
Messages
1 877 056
Membres
160 560
dernier inscrit
jesaispas
Haut Bas