Macro "complexe" de tri entre workbook

Bonjour à tous amis codeurs,

Bon, je suis complètement bloqué dans un de mes travail, je fais un assez gros fichier avec des macros pour limiter des erreurs de mes collègues mais là je rame complet.

J'ai un premier fichier Excel avec plusieurs macros dedans, la seule feuille qui nous intéresse c'est la sectionsa_l.

Dedans il y a tout pleins de trucs mais le bouton (1. Remplissage auto) permet de compléter la sheet en fonction des première infos du tableau.

Lorsque l'on clique dessus il y a notamment les colonnes AT, BC et BM qui se remplissent, ce sont des types de joints (de la forme SS_JA, SS_JC, SI_JA, SI_JC, A_JA, A_JC plus des chiffres).

Ce que je veux (attention faut accrocher son slip) c'est:

1. Copier ces données vers un autre document Excel, qui se nomme Liste_joint, dans la première colonne.

2. Supprimer les doublons et les cases vides (parce que les types de joints vont par deux mais ce que je veux c'est une liste exhaustive des types de joints).

3. Les trier par ordre croissant.

Je m'explique:

De mon premier fichier j'extrait les données, je fais ma macro et ça marche plutôt bien. Mon problème c'est que j'ai une deuxième sheet, identique à la première, qui peut avoir des données différentes, je dois effectuer les mêmes opérations et les rajouter dans le même tableau.

Ce sont les fonctions de suppression des doublons, de suppression des cases vides et de tri par ordre croissant sur une zone variable qui me bloquent...

Donc en gros 3 fichiers:

  • Premier fichier parent avec la macro qui nous intéresse: Poutre_left, la sheet qui nous intéresse est sectionsa_l, dedans il y a les données que je veux extraire qui sont elles mêmes issues d'une macro. C'est la macro Liste_joint qui doit faire le travail.
  • Deuxième fichier parent: Poutre_right, sheet sectionsa_r, il y a là la deuxième plage de données qui nous intéresse.
  • Troisième fichier: Liste_joint, c'est dans ce dernier que je dois faire apparaître ma liste de joint.

Pour voir ce que je veux faire vous pouvez cliquer sur le bouton "6.Liste joint" qui exécute la première partie de la macro correctement (une fenêtre s'ouvre pour sélectionner le fichier Liste_joint au début de la macro) vous aurez ainsi une idée de ce que je veux faire.

Si vous voulez plus d'explication pour comprendre mon code (qui n'est clairement pas propre je code depuis peu :/) n'hésitez pas !

Même si personne ne se lance pour faire le code (je comprend c'est le bordel xD), si certains ont des astuce pour les fonctions de tri, suppression des cases vides et doublons avec des variables je suis preneur.

Aussi si vous avez des commentaire sur mon code, comment le faire plus proprement et simplement je suis preneur

En tout cas merci d'avance à tout ceux qui s'y intéresseront

Les Tyrannosaure vaincront !!!

3liste-joint.xlsx (10.77 Ko)
2poutre-left.xlsm (266.67 Ko)
2poutre-right.xlsm (243.45 Ko)

Bonjour et sur le forum,

Je te propose un code qui permet d'exporter les valeurs de joints sans doublons:

3poutre-left.xlsm (262.88 Ko)

Le code:

Sub test()
Dim ligDep As Integer, ligFin As Long, ligExport As Long
Dim tabDep As Variant
Dim colec As New Collection
Dim WkbCible As Workbook
Dim nomFichier As String

'initialisations
ligDep = 7
ligFin = Range("a" & Rows.Count).End(xlUp).Row
tabDep = Range("a" & ligDep, "bm" & ligFin)

On Error Resume Next
For i = LBound(tabDep, 1) To UBound(tabDep, 1)
    'col at: 46
    If tabDep(i, 46) <> "" Then
        colec.Add tabDep(i, 46), tabDep(i, 46)
    End If
    'col bc: 55
    If tabDep(i, 55) <> "" Then
        colec.Add tabDep(i, 55), tabDep(i, 5)
    End If
    'col bm: 65
    If tabDep(i, 65) <> "" Then
        colec.Add tabDep(i, 65), tabDep(i, 65)
    End If
Next i

'export
If colec.Count > 0 Then
    'ouverture fichier
    Set WkbCible = Workbooks.Open("Liste_joint")
    Set WkbCible = Workbooks("Liste_joint")

    'si problème d'ouverture
    If WkbCible Is Nothing Then
        MsgBox "Le fichier n'a pas pu être ouvert, merci de l'ouvrir manuellement.", vbInformation, "Information"
        nomFichier = Application.GetOpenFilename
        WkbCible = Workbooks.Open(nomFichier)

        'si ça bloque toujours
        If WkbCible Is Nothing Then
            MsgBox "Le fichier n'a toujours pas pu être ouvert.", vbCritical, "Erreur"
            Exit Sub 'sortie du programme
        End If
    End If
    On Error GoTo 0

    'export des données
    With WkbCible.Sheets(1)
        ligExport = .Range("a" & .Rows.Count).End(xlUp).Row + 1
        For i = 1 To colec.Count
            .Cells(ligExport + i - 1, 1) = colec(i)
        Next i
    End With

    'Tri
    With WkbCible.Sheets(1).Sort
        .SortFields.Clear
        .SortFields.Add Key:=Range("A2"), SortOn:=xlSortOnValues, Order:=xlAscending, DataOption:=xlSortNormal
        .SetRange Range("a2", "a" & ligExport + colec.Count - 1)
        .Header = xlNo
        .MatchCase = False
        .Orientation = xlTopToBottom
        .SortMethod = xlPinYin
        .Apply
    End With
End If
End Sub

L'astuce, c'est que j'utilise une collection avec comme clé le nom du joint, et comme valeur, le nom du joint, une collection ne peut pas avoir deux clés identiques, elle renvoie une erreur que j'ignore et je passe à la suite, ainsi, elle n'aura qu'une fois le nom de chaque joint.

Bordel Ausecour tu gères <3

Je sais pas si c'est trop te demander mais est ce que tu sais si c'est possible de 'sélectionner' une partie de tableur avec des variables pour y faire des opérations ?

Parce que le code pour supprimer les cases vide par exemple je sais le faire, je peux l'adapter, mais je m'y connais pas assez pour le faire avec des variables. Comme tu as sans doute pu le voir je suis pas un as en ce qui concerne le code :/ promis je prendrais des cours pour faire des trucs propres !

En tout cas merci beaucoup pour ce que tu as fait, t'es génial

Re,

Quelque chose comme ça?

Sub test()
Dim ligFin As Long
ligFin = Range("a" & Rows.Count).End(xlUp)

For i = ligFin To 2 Step -1
    If Range("b" & i) = "" Then
        Range("b" & i).EntireRow.Delete shift:= xlShiftUp
    End If
Next i
End Sub

Salut Ausecour, le forum

J'avoue que j'ai strictement mais rien compris à ton dernier code Ausecour xD (excusez moi j'ai du mettre en stand by ce projet pendant quelques temps)

Le seul truc que j'ai pu décrypter c'est "EntireRow.Delete shift:= xlShiftUp"

Mais le reste je comprends pas, en fait c'est la base du truc que je comprend pas, je m'explique:

-ligFin = Range("a" & Rows.Count).End(xlUp) ==> Je comprend que tu sélectionne une plage mais le reste... ^^ c'est quoi le "a" et je vois un concaténer mais pareil je bite rien :/

-For i = ligFin To 2 Step -1 ==> Pareil

Et du fait de pas comprendre le début ne m'aide pas pour la fin xD Je me doute que ça marche mais je préfère comprendre pour l'incrémenter à ce que j'ai déjà fais, aurais- tu l'extrême amabilité de bien vouloir m'expliquer au saint Dieu du VBA ? :3

Merci d'avance,

Sinon pour la macro d'ouverture de fichier et de tri ça marche du feu de Dieu sauf un détail quand il ne trouve pas le fichier et que je dois aller le sélectionner même en l'ouvrant il passe en erreur critique, le fichier s'ouvre bien mais il sort de la macro, pourtant le WkbCible doit bien être égal à quelque chose...

 'si problème d'ouverture
    If WkbCible Is Nothing Then
        MsgBox "Le fichier n'a pas pu être ouvert, merci de l'ouvrir manuellement.", vbInformation, "Information"
        nomFichier = Application.GetOpenFilename
        WkbCible = Workbooks.Open(nomFichier)

        'si ça bloque toujours
        If WkbCible Is Nothing Then
            MsgBox "Le fichier n'a toujours pas pu être ouvert.", vbCritical, "Erreur"
            Exit Sub 'sortie du programme
        End If
    End If

En tout cas merci beaucoup

Bonjour à toi,

ouf vieux sujet

ça va, ce que tu demandes ne nécessite pas que je me rappelle à 100% de ton sujet, alors pour les explications:

Pour le Range("a" & Rows.Count), la raison pour laquelle je mets tout ça, c'est que normalement, pour faire référence à une plage de cellules en VBA, tu as 3 façons de faire: Range("A1") pour cellule A1, Range("A1:B2") pour la plage A1:B2, Range("A1","B2") pour la plage A1:B2. En gros, il faut fournir à Range du texte contenant les références de ta plage, là où la fonction concatener sert, c'est que je sais que je veux chercher la dernière ligne remplie en colonne A, ça c'est constant, donc je mets "a" pour faire référence à cette colonne, ensuite avec la fonction concatener, j'ajoute à ma référence une variable Rows.Count qui contient le nombre de lignes de la feuille (qui peut être variable en fonction des versions d'Excel). Ainsi, si Rows.Count est égal à 10 000 par exemple, ça donnera: "a" & 10000 = "a10000". Avec ça je fais référence à la dernière cellule colonne A, il ne me reste ensuite qu'à remonter avec .End(xlUp) pour aller sur la dernière cellule remplie en colonne A, et renvoyer son numéro de ligne avec .Row.


Pour la boucle For, la forme que l'on voit le plus souvent c'est:

For i = 1 to 10
    'code qui va se répéter 10 fois
Next i

premier tour de boucle: i = 1, deuxième tour de boucle i = 2, jusqu'à i = 10 puis la boucle se finit.

Ici un paramètre est caché, c'est Step qui définit de combien change la variable i, à chaque fois que tu passes sur la ligne Next i qui te renvoie au début du For, et donc au début de la boucle. Si ici je mets par exemple:

For i = 0 to 10 Step 5
    'code qui va se répéter 3 fois
Next i

i va prendre les valeurs i = 0, i = 5, i = 10, puis la boucle va s'arrêter.

Dans le code, l'astuce c'est que comme on va supprimer des lignes, on va changer progressivement le numéro de la dernière ligne à traiter, le plus simple c'est donc de partir de la dernière ligne pour revenir à la première (la 2), et de supprimer progressivement les lignes.

C'est pour ça que je mets:

For i = ligfin to 2 Step -1

Next i

Si ligfin = 10 par exemple, i va faire: i = 10, i = 9 ... i = 2, puis sortie de la boucle.


Pour ton problème avec WkbCible, ça vient de la façon dont tu lui affectes sa valeur selon moi, vois-tu, pour une simple variable comme i, il faut juste faire i = 2, sauf que la c'est un classeur que tu cherches à enregistrer, il s'agit donc d'un objet qui est très différent d'une variable. Si tu prends un stylo par exemple, il a plusieurs variables, sa couleur, sa marque, la quantité d'encre, et une "méthode" qui lui permet d'écrire, par exemple tu fais stylo.ecrire("coucou"), il mettra sur ta feuille "coucou". Ce que tu as à retenir pour le moment, c'est que ça n'a rien à voir avec une variable, ici tu ne passes pas une valeur, mais un objet, il faut donc utiliser le mot clé "Set" qui permet de définir un objet.

WkbCible = Workbooks.Open(nomFichier)

devrait s'écrire:

Set WkbCible = Workbooks.Open(nomFichier)

Sans dec Ausecour, t'es prof de VBA/Excel ?

Explications super claires et concises, rien à redire, merci beaucoup,

Je vais tâcher d'adapter ça au mieux de mes compétences,

Merci milles fois

Rechercher des sujets similaires à "macro complexe tri entre workbook"