Microsoft 365 Insérer des lignes dans un tableau en décalant celles du dessous

Léraud Florian

XLDnaute Junior
Bonjour Bonjour =)

J'aimerai savoir s'il est possible de copier des cellules d'un tableau pour ensuite les coller en dessous mais en décalant les lignes situées au dessous.

J'aimerai copier les cellules comprises entre F11 et F15 et les coller juste en dessous avec une ligne d'écart et en gardant les lignes inférieures. J'arrive à les copier et coller avec le code ci-dessous mais il écrase les informations du dessous :/

VB:
Sub copie_decal()

Dim i As Integer
Dim A As String

Dim plage As Range, nb_copie As Long
A = MsgBox("Voulez-vous saisir un nouveau chantier ?", vbYesNo + vbQuestion)
If A = vbYes Then
nb_copie = 1
Set plage = Range("F11:F16")
For i = 1 To nb_copie
    plage.Copy plage.Offset(plage.Rows.Count * i, 0)
    Cells(plage.Rows.Count * (i + 1) + i, 1).Value = Cells(plage.Rows.Count, 1)
Next i
End If
End Sub

PS : je sais que mes lignes de codes pourraient en faire vomir certains car très lourdes ^^

Mon fichier en PJ

Merci d'avance =)
 

Pièces jointes

  • Planning avancé.xlsm
    494.6 KB · Affichages: 15
Solution
Hello @Phil69970

je me permet de reprendre ta macro telle quelle pour l'intégrer dans le fichier ci joint
@Léraud Florian
j'ai aussi mis le code de ta fonction "copie décal" pour insérer les lignes dans ton tableau
comme il s'agit d'un tableau struturé, j'en ai profité pour corriger le code de l'évènement change de la feuille 2022 pour que Vacances soit toujours mis à la dernière ligne

vgendron

XLDnaute Barbatruc
Hello

Effectivement.. tes macros sont très lourdes et pas du tout optimisées
exemple de la macro que lances à chaque fois que tu selectionnes une cellule dans la feuille "2022"
il vaudrait mieux lancer cette macro uniquement lorsqu'il y a un changement de valeur dans une cellule
ca donnerait cette macro simplifiée
VB:
Private Sub Worksheet_Change(ByVal Target As Range)
Application.ScreenUpdating = False 'on désactive le refresh
Application.EnableEvents = False 'on désactive les évènements.. sinon.. cettte macro sera appelée en boucle==> plantage
Application.Calculation = xlCalculationManual

With ActiveSheet 'dans la feuille active
    LastCol = .Cells(5, .Columns.Count).End(xlToLeft).Column 'dernière colonne non vide de la ligne 5
    For j = 7 To LastCol 'pour chaque colonne de G à LastCol
        Nombre = Application.WorksheetFunction.CountIf(.Cells(6, j).Resize(5, 1), 0) 'on compte le nombre de 0 sur les 5 lignes
        .Cells(21, j) = IIf(Nombre <> 0, "Vacances", "") 'on met vacances ou rien selon le résultat
        .Columns(j).AutoFit 'on ajuste la largeur de la colonne
    Next j
End With
Application.Calculation = xlCalculationAutomatic 'on réactive
Application.EnableEvents = True
Application.ScreenUpdating = True
End Sub

en ce qui concerne ta question: c'est toujours sur la feuille "2022" ?
tu souhaites inserer 5 lignes dans le tableau ?
 

Phil69970

XLDnaute Barbatruc
Bonjour @Léraud Florian , @vgendron

Dans la même idée d'optimisation

Tu peux remplacer toute ta macro "chantier" (Module 13) par :

VB:
Sub Chantier()
'Dim A$, B$, D$, Semaine$, Chantier$ '==> c'est équivalemnt à la ligne ci dessous
Dim A As String, B As String, D As String, Semaine As String, Chantier As String

With Sheets("2022") 'dans la feuille 2022

    A = MsgBox("Voulez-vouis saisir un nouveau chantier ?", vbYesNo + vbQuestion)

    If A = vbNo Then
        Close A
    Else
        B = InputBox("Quel est le chantier ?", "Nom du chantier", "Nom du chantier")
       
        If B = "Nom du chantier" Or B = " " Or B = "" Then
            MsgBox "Veuillez entrez un nom de chantier", vbExclamation
        Else
            Semaine = InputBox("Quelle est la semaine concernée ?", vbOKCancel)
           
            If Semaine < 0 Or Semaine > 52 Then
                MsgBox "Veuillez entrer un nombre entre 1 et 52", vbExclamation
            Else
                BE = InputBox("Combien de temps de travail au BE ?", vbOKCancel)
                Fab = InputBox("Combien de temps de travail pour la fabrication ?", vbOKCancel)
                Fini = InputBox("Combien de temps de travail pour la finition ?", vbOKCancel)
                Pose = InputBox("Combien de temps de travail pour la pose ?", vbOKCancel)
               
                Cells(11, Semaine + 6) = "- " & B       '  + 6 car il y a 6 colonnes avant les colonnes des semaines
                Cells(12, Semaine + 6) = BE             '  + 6 car il y a 6 colonnes avant les colonnes des semaines
                Cells(13, Semaine + 6) = Fab            '  + 6 car il y a 6 colonnes avant les colonnes des semaines
                Cells(14, Semaine + 6) = Fini           '  + 6 car il y a 6 colonnes avant les colonnes des semaines
                Cells(15, Semaine + 6) = Pose           '  + 6 car il y a 6 colonnes avant les colonnes des semaines
                AutoColumnLength Cells(11, Semaine + 6) '  + 6 car il y a 6 colonnes avant les colonnes des semaines
                MsgBox "Le chantier " & B & " est crée", vbInformation, "Nom du chantier"
            End If
        End If
    End If
End With
End Sub

Avec nos 2 codes d'optimisation cela devient plus digeste.;)

Pour ta question il nous manque des précisions

@Phil69970
 

Phil69970

XLDnaute Barbatruc
Le fil

Et tu peux remplacer toute ta macro "ResetChantier" (Module 13) par :
VB:
Sub ResetChantier()
Dim Semaine$
With Sheets("2022")
    Semaine = InputBox("Quelle semaine voulez-vous supprimer ?", vbOKCancel)
                   
    Cells(11, Semaine + 6).ClearContents    ' + 6 car il y a 6 colonnes avant les colonnes des semaines
    Cells(12, Semaine + 6).ClearContents    ' + 6 car il y a 6 colonnes avant les colonnes des semaines
    Cells(13, Semaine + 6).ClearContents    ' + 6 car il y a 6 colonnes avant les colonnes des semaines
    Cells(14, Semaine + 6).ClearContents    ' + 6 car il y a 6 colonnes avant les colonnes des semaines
    Cells(15, Semaine + 6).ClearContents    ' + 6 car il y a 6 colonnes avant les colonnes des semaines

End With

End Sub

Si j'ai compris, on fait +6 parce que je commence la colonne Semaine à la colonne F ?

Colonne 6 = Colonne F
Colonne 7 = Début des semaines
1657013700782.png


Si tu es à la semaine 1 par exemple tu es donc à la colonne 6 (F) + 1 (N° de la semaine choisi) donc colonne 7 ==> G

Est ce que je t'ai perdu ? 🤣

Ton fichier commence à devenir digeste ;)

@Phil69970
 

vgendron

XLDnaute Barbatruc
Hello @Phil69970

je me permet de reprendre ta macro telle quelle pour l'intégrer dans le fichier ci joint
@Léraud Florian
j'ai aussi mis le code de ta fonction "copie décal" pour insérer les lignes dans ton tableau
comme il s'agit d'un tableau struturé, j'en ai profité pour corriger le code de l'évènement change de la feuille 2022 pour que Vacances soit toujours mis à la dernière ligne
 

Pièces jointes

  • Planning avancé.xlsm
    478.3 KB · Affichages: 6

vgendron

XLDnaute Barbatruc
Je regarde

en attendant, une autre optimisation
toutes les macros 'identiques" dans le code des différentes feuilles peuvent etre supprimées et remplacées par ce code unique dans le code du "ThisWorkbook"
VB:
Private Sub Workbook_SheetSelectionChange(ByVal Sh As Object, ByVal Target As Range)
If Target.Offset(0, -1) <> "Semaine" Then Exit Sub
Application.EnableEvents = False
ligne = Target.Row
Colonne = Target.Column
A = MsgBox("Est-ce une semaine de vacances ?", vbYesNo, "Vacances")
             
If A = vbYes Then

    Cells(ligne + 6, Colonne).Resize(1, 9) = 0
    Cells(ligne + 23, Colonne) = 7
Else
    formule = "=MAX(0,C" & ligne + 3 & "-$C$" & ligne + 23 & "*8-C" & ligne + 5 & "*8)"
    Cells(ligne + 6, Colonne).Resize(1, 9).Formula = formule
    
    Do
        B = InputBox("Combien de four fériés (entre 0 et5) ?", vbQuestion)
        
        If B = "" Then B = -1
        If Not IsNumeric(B) Then B = -1
        
    Loop Until CDbl(B) >= 0 And CDbl(B) <= 5
    
    Range("C" & ligne + 23) = CDbl(B)
    
End If

Application.EnableEvents = True
End Sub
 

vgendron

XLDnaute Barbatruc
je n'ai pas encore revu la formule, mais j'ai simplifié les macros de saisie de congés et reset congés
==> j'ai supprimé tous les modules qui sont devenus inutiles
il faut que tu réaffectes TOUS tes boutons à ces deux macro (je l'ai fait pour les mois de janvier et février pour le test)

principe:
selon le bouton sur lequel tu cliques, la macro récupère (dans le texte du bouton) le numéro de la semaine
et donc. trouve le numéro de ligne à traiter
selon le salarié, la macro trouve quelle colonne il occupe

ensuite. y a plus qu'à mettre les infos souhaitées

idem pour la macro reset: selon le texte du bouton, elle trouve sur quelles lignes il faut intervenir
je te laisse regarder le code: j'y ai mis des commentaires
 

Pièces jointes

  • Planning avancé.xlsm
    269.6 KB · Affichages: 8

vgendron

XLDnaute Barbatruc
Cependant, j'ai un petit soucis, il me met incompatibilité de type avec ligne lorsqu'on lance la macro pour savoir si c'est une semaine de vacance et qu'on clique sur non :

oui j'ai vu le problème aussi, c'est quand tu cliques sur la colonne A==> target.offset(0,-1) n'existe pas. donc. il aime pas
j'ai corrigé dans la version que je viens de poster
 

vgendron

XLDnaute Barbatruc
Si j'enlève les deux lignes :

le problème vient de la cellule fusionnée qui contient le numéro de semaine: elle est considérée comme une plage de 9 colonnes..donc le code n'est pas executé

remplace le code par celui ci

VB:
Private Sub Workbook_SheetSelectionChange(ByVal Sh As Object, ByVal Target As Range)

If Range("B" & Target.Row) <> "Semaine" Then Exit Sub
Application.EnableEvents = False
ligne = Target.Row
colonne = 3
A = MsgBox("Est-ce une semaine de vacances ?", vbYesNo, "Vacances")
            
If A = vbYes Then

    Cells(ligne + 6, colonne).Resize(1, 9) = 0
    Cells(ligne + 23, colonne) = 7
Else
    formule = "=MAX(0,C" & ligne + 3 & "-$C$" & ligne + 23 & "*8-C" & ligne + 5 & "*8)"
    Cells(ligne + 6, colonne).Resize(1, 9).Formula = formule
    
    Do
        B = InputBox("Combien de four fériés (entre 0 et5) ?", vbQuestion)
        
        If B = "" Then B = -1
        If Not IsNumeric(B) Then B = -1
        
    Loop Until CDbl(B) >= 0 And CDbl(B) <= 5
    
    Range("C" & ligne + 23) = CDbl(B)
    
End If

Application.EnableEvents = True
End Sub
 

vgendron

XLDnaute Barbatruc
pour le fun, une V3 qui permet la saisie des congés via un formulaire
pour le lancer: bouton "Sasie de congés via formulaire" sur la feuille 2022

cela m'a permis de voir un problème dans tes feuilles
tes semaines ne sont pas forcément sur la bonne feuille
exemple de la semaine 5: cette année, elle a commencé le 31 Janvier==> elle appartient donc au mois de janvier

la règle que j'ai utilisée: la semaine 1 de l'année commence au 1er lundi de l'année
ex en 2022: 1 et 2 janvier étaient des samedi et dimanche
le 1er lundi de l'année est le 03/01/2022==> la semaine 1 est donc du 03 au 09 janvier, semaine 2: 10 au 16.....
 

Pièces jointes

  • Planning avancé V3.xlsm
    287.1 KB · Affichages: 5

vgendron

XLDnaute Barbatruc
en V4, avec la dernière macro qui restait à simplifier

question:
la macro "copie_decal" te sert à insérer des lignes dans le tableua de la feuille 2022

mais du coup.. ca te sert à quoi? pour une meme semaine, tu peux avoir plusieurs chantiers?

la macro Chantier tu permet d'ajouter un chantier sur une semaine : MAIS
1) elle ne vérifie pas si tu n'est pas en train d'écraser un chantier existant
2) elle ne permet de mettre un chantier QUE sur les premières lignes (11 à 15)
du coup ca te sert à quoi d'insérer des lignes (avec la macro copie_decal) si tu ne peux jamais y mettre de chantier??==> je m'attend à ce que tu nous dises que tu aimerais pouvoir enregistrer un chantier sur ces nouvelles lignes==> à quelles conditions?

la macro ResetChantier: de la même manière que pour la macro précédente, tu ne peux effacer QUE sur les lignes 11 à 15
 

Pièces jointes

  • Planning avancé V4.xlsm
    281.3 KB · Affichages: 10

vgendron

XLDnaute Barbatruc
Hello
le pb ne vient pas du code, mais de la syntaxe de tes entetes de lignes et donc de la formule

les 5 derniières lignes, sont écrites avec la structure:
"Heures XX restantes / Semaine " ==> avec un espace à la fin après Semaine: SAUF sur la dernière ligne
les 5 lignes "insérées" sont écrites avec la structure:
"Heures XX / Semaine sur chantier"

la formule utilisée compare les intitulés pour savoir s'il faut prendre la valeur de la colone en compte
pour ca, la formule remplace "restantes " par "" et ajoute "sur chantier" sur les 5 dernières lignes


la présence ou absence d'un espace sur une des lignes fait que la formule conclue qu'il s"agit de deux lignes différentes
"Heures pose restantes / Semaine" (pas d'espace à la fin) est transformée en
"Heures pose / Semainesur chantier" ==>manque un espace
pour etre comparée à "Heures pose / Semaine sur chantier" ==> la c'est KO:
pS: je te fais grace du s manquant à restantes

alors que "Heures BE restantes / Semaine " (avec un espace à la fin) est transformée en
"Heures BE / Semaine sur chantier" pour etre comparée à "Heures BE / Semaine sur chantier"==> OK

pour résumer: tu as un espace manquant en fin de cellule G20

mais comme je n'ai jamais compris l'interet de mettre des espaces en fin de chaine, je traite le pb à l'envers. en enlevant tous les espaces de fin de cellules dans les lignes 17 à 19, et j'ai modifié la formule

donc;. en PJ, le pb est corrigé
 

Pièces jointes

  • Planning avancé V4.xlsm
    283.1 KB · Affichages: 8

vgendron

XLDnaute Barbatruc
bonjour

dans le code, Nombre est bien le nombre de 0 sur les 4 lignes..==> ca peut donc etre 0 1 2 3 ou 4

la ligne du dessous qui met le mot vacances regarde si Nombre<>0==> pour 1 2 3 et 4 le mot vacances est mis

si tu ne veux vacances QUE pour le cas ou il y a 4 fois 0.. il faut corriger la ligne par
VB:
.Range(LastLine + 1, j) = IIf(Nombre = 4, "Vacances", "")
 

Léraud Florian

XLDnaute Junior
Bonjour et merci de votre réponse =)

J'ai pris note de votre conseil et j'ai créé une macro pour lancer l'actualisation de la feuille 2022.

Merci pour votre programme qui met beaucoup moins de temps ^^

Oui en fait je veux, dans la feuille 2022, pouvoir choisir un "nouveau chantier" et si oui, alors il copie les cellules F11 jusqu'à F15 en dessous afin de pouvoir rentrer un nouveau chantier.
 

Discussions similaires

Membres actuellement en ligne

Aucun membre en ligne actuellement.

Statistiques des forums

Discussions
312 206
Messages
2 086 219
Membres
103 158
dernier inscrit
laufin