Copie sans écraser

Bonjour à tous,

Débutant autant qu'on peut l'être en macro je requière de l'aide auprès de vous.

Je souhaite créer une macro me permettant de copier une ligne en fonction d'une valeur de cellule dans une seconde feuille:

Feuille "Tableau", si la valeur de la colonne C est égale à "ok", déplacer vers feuille "Archives"

La copie et suppression marchent bien (en fait j'ai réussit à adapter à mon tableau ce que j'ai trouvé ci et la mais je n'ai aucune idée de la fonction de telle ou telle commande), par contre le problème est que chaque exécution de la macro vient écraser les lignes précédemment copier dans "Archives" au lieux d'ajouter à la suite.

Voilà le code:

Sub Archive()
    Dim PlageUtile As Range
    Dim Ligne As Range
    Dim Origine As Worksheet
    Dim Destination As Worksheet
    Dim LigneDestination As Integer

    Set Origine = Worksheets("Tableau")
    Set Destination = Worksheets("Archives")
    Set PlageUtile = Range(Origine.Cells(1, 1), Origine.Cells(1, 1).SpecialCells(xlLastCell))

    LigneDestination = 1

    For Each Ligne In PlageUtile.Rows
        If Ligne.Cells(1, 3).Value = "ok" Then
            Ligne.Copy Destination.Cells(LigneDestination, 1)
            LigneDestination = LigneDestination + 1
            Ligne.EntireRow.Delete
        End If    
    Next
End Sub

J'imagine qu'il doit pas manquer grand chose mais je sèche complétement .

Merci d'avance pour votre expertise!

Bonjour,

Si tu pouvais :

1) Eviter de sauter des lignes (ce qui fait scroller en permanence)

2) Indenter ton code

3) Le mettre sous balises Code dans le post

déjà, ça deviendrait lisible, sans trop d'effort.

Cordialement.

Voilà je pense que c'est mieux .

Par contre je ne sais pas ce que veut dire "indenter".

Merci,

C'est beaucoup mieux !

Et si tu sais pas ce que veut dire "indenter", tu as pourtant indenté parfaitement dans les règles !

Ton code peut être amélioré (si tu le souhaites), mais commençons par le problème posé...

LigneDestination = Destination.Cells(Rows.Count, 1).End(xlUp).Row + 1

Cette modification te permettra de ne pas écraser ce qui précède.

Je conseille que ta feuille Archives soit doté d'une ligne d'en-tête au départ, c'est plus sûr, le résultat sera donc 2 la première fois, et ensuite cela prendra la ligne suivante...

Ca marche parfaitement !

Merci pour la réponse (très très) rapide et chapeau pour l'efficacité!

Pourquoi pas améliorer le code, que proposes-tu?

Merci,

Bonjour,

Je reste très proche de ton code et opère juste quelques aménagements...

Travaillant uniquement sur le code, il convient de s'assurer que ce n'est pas en contradiction avec ta configuration.

Sub Archive()
    Dim PlageUtile As Range, Ligne As Range, Destination As Worksheet
    Dim LigneDestination As Integer, NbCol As Integer
    Set Destination = Worksheets("Archives")
    LigneDestination = Destination.Cells(Rows.Count, 1).End(xlUp).Row + 1
    With Worksheets("Tableau")
        Set PlageUtile = .Range(.Cells(1, 1), .Cells(1, 1).SpecialCells(xlCellTypeLastCell))
    End With
    NbCol = PlageUtile.Columns.Count
    Application.ScreenUpdating = False
    For Each Ligne In PlageUtile.Rows
        If Ligne.Cells(1, 3).Value = "ok" Then
            Destination.Cells(LigneDestination, 1).Resize(, NbCol).Value = Ligne.Value
            LigneDestination = LigneDestination + 1
            Ligne.Cells(1, 1).ClearContents
        End If
    Next Ligne
    PlageUtile.Columns(1).SpecialCells(xlCellTypeBlanks).EntireRow.Delete
End Sub

1) Je garde tes noms de variables , bien que ma préférence aille à des noms courts (et qu'au-delà de 3 caractères je commence à trouver que ça s'allonge... ), mais ce serait un aménagement sans incidence, très perso...

Je supprime ta variable Origine, qui n'a guère d'utilité une fois définie PlageUtile... J'ajoute par contre une variable NbCol pour recueillir le nombre de colonnes de PlageUtile (voir plus loin utilisation).

2) Initialisation des variables : Destination, LigneDestination, PlageUtile et NbCol. Rien de différent...

3) Inhibition de la mise à jour de l'affichage (ScreenUpdating) : indispensable pour accélérer l'exécution du code, car tu opères des modifications se répercutant sur l'affichage.

4) Habituellement dans une configuration de ce type, opérant un transfert de données d'une feuille vers une autre, je mets la première sous bloc With et la seconde sous variable, ce qui apparaît à l'usage comme l'un des compromis les plus optimal.

Ici, j'ai voulu ton choix de définition préalable de la plage d'intervention, car il est aussi bon ! Et sa mise sous bloc With ne se justifiait pas dans la mesure où son utilisation dans une boucle For Each a un effet comparable de mise en mémoire par VBA.

En second lieu, je procède habituellement à une mise en tableau des lignes à transférer, pour éviter les opérations individuelles et ne faire qu'une affectation globale à la fin. Je ne l'ai pas fait ici car les conditions dans lesquelles monter le tableau ne me semblaient pas devoir apporter un gain indubitable... Ce serait éventuellement à tester sur un transfert d'une assez grande quantité de lignes pour pouvoir mesurer un effet qui deviendrait perceptible. (Note toutefois que l'utilisation de tableaux est l'un des principaux moyens pour rendre plus rapide l'exécution du code.)

Petite remarque à ce stade : pour quelqu'un qui se prétend débutant, je dois constater que tes choix ne sont pas spécifiquement des choix de débutant ! J'aurais apprécié d'être en mesure d'opérer des choix similaires à mes débuts...

5) Petit changement notable : plus de copier-coller, on procède par affectation de valeurs du type PlageB.Value = PlageA.Value (les 2 plages étant de taille identique, et étant entendu que l'on n'a que des valeurs à transférer). D'où l'utilisation du nombre de colonnes pour dimensionner la plage de destination à la taille de la ligne source. Méthode à privilégier par rapport au copier-coller, dès lors qu'elle peut être appliquée, car plus rapide.

6) Autre changement : on ne supprime pas les lignes au fur et à mesure, on se contente d'effacer une cellule (en colonne A), opération plus légère, donc plus rapide, qui permettra la suppression globale des lignes à supprimer à la fin...

7) Suppression des lignes en utilisant SpecialCells sur la colonne on l'on a procéder à des effacements.

A tester après vérification...

Cordialement.

Bonjour,

J'ai testé ton code et tout marche parfaitement!

Pour le code que j'ai utilisé je l'ai tout simplement copier d'un post et adapté à mon fichier

Non pas que je n'aime pas les compliments mais je préfère les mériter ^^.

En tout cas merci bien pour ton expertise, je l’apprécie à ça juste valeur .

Cdt,

Rechercher des sujets similaires à "copie ecraser"