Problème de scrollbar (fallait bien que ca m'arrive! ;))

Fermé
Pr.Witherfire - 14 janv. 2023 à 14:45
Phil_1857 Messages postés 1872 Date d'inscription lundi 23 mars 2020 Statut Membre Dernière intervention 28 février 2024 - 17 janv. 2023 à 09:56

Bonjour. J'ai un probléme. Je voudrais "tout simplement" qu'une scrollbar fasse défiler un canvas.

Mon code:

from tkinter import *

PCHIFMenu = Tk()
PCHIColor2 = "Red"
PCHIColor1 = "Blue"
PCHIPolice = "Arial"

PCHIFMenu.title("Maths")
PCHIFMenu.geometry("1600x900+-8+0")

PCHIFrameDOMenu = Frame(PCHIFMenu, width=500, height=500)
PCHISbDOMenu = Scrollbar(PCHIFrameDOMenu, orient=VERTICAL)
PCHISbDOMenu.pack(side=RIGHT, fill=Y)




PCHICDocOffiMenu = Canvas(PCHIFrameDOMenu, width=400, height=900, bg=PCHIColor1)

PCHICDocOffiMenu.config(width=300, height=300)
PCHICDocOffiMenu.config(yscrollcommand=PCHISbDOMenu.set)
PCHISbDOMenu.config(command=PCHICDocOffiMenu.yview)

PCHICDocOffiMenu.create_line(0, 60, 400, 60, fill=PCHIColor2)
PCHICDocOffiMenu.create_line(0, 61, 400, 61, fill=PCHIColor2)
PCHICDocOffiMenu.create_line(0, 62, 400, 62, fill=PCHIColor2)

PCHILtDO1 = Label(PCHIFMenu, text="Débutant", fg=PCHIColor2, bg=PCHIColor1, font=(PCHIPolice, 25))

PCHILtDO1.place(x=200, y=125)
PCHIFrameDOMenu.place(x=0, y=0)






def PCHIFoOuvDO(Cat):

    # MAJ Bouton
    globals()["PCHIBDO"+str(Cat)] = Button(PCHIFMenu, text= "<", font=(PCHIPolice,35), bg=PCHIColor1, fg=PCHIColor2, bd=0,height=1, command= lambda: PCHIFoFerDO(int(Cat)))







    if Cat == 1:

        globals()["PCHIBDO" + str(Cat)].place(x=20, y=111)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="1", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=200)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="2", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=300)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="3", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=400)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="4", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=500)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="5", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=600)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="6", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=700)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="7", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=800)

        PCHIFrameTutoVariables = Frame(PCHIFMenu, bg=PCHIColor1, width=400, height=100)
        PCHILtTutoVariables = Button(PCHIFrameTutoVariables, bg=PCHIColor1, text="8", font=(PCHIPolice, 25), fg=PCHIColor2, bd=0)
        PCHILtTutoVariables.place(x=160, y=10)
        PCHIFrameTutoVariables.place(x=0, y=900)


    if Cat == 2:

        globals()["PCHIBDO" + str(Cat)].place(x=20, y=211)

    if Cat == 3:

        globals()["PCHIBDO" + str(Cat)].place(x=20, y=311)



PCHIBDO1 = Button(PCHIFMenu, text= "^", font=(PCHIPolice,35), bg=PCHIColor1, fg=PCHIColor2, bd=0,height=1, command= lambda : PCHIFoOuvDO(1))

PCHIBDO1.place(x=20, y=111)

PCHISbDocOffiMenu = Scrollbar(PCHICDocOffiMenu)
PCHISbDocOffiMenu.place(x=375, y=0)
PCHISbDocOffiMenu.config(command = PCHICDocOffiMenu.yview )

PCHICDocOffiMenu.place(x=0, y=0)


PCHIFMenu.mainloop()

Merci

5 réponses

Bonsoir.

Le plus gros de tes problèmes est que tu ne tiens aucunement compte des recommandations que tout le monde te fais chaque fois...

- Aucun intérêt de préfixer tes variables par PCHI truc machin, une variable, c'est soit camelCase, soit snake_case, en python la recommandation est le snake_case sauf pour les noms de classes, le camelCase est recommandé (il me semble), maintenant certains font à leur manière en gardant une cohérence, mais certainement pas en nommant tout de la même façon, variables, fonctions, constantes... Personellement, je ne vois pas comment on pourrait se souvenir du nom d'une fonction comme « PCHIFoOuvDO », à part le copié/collé de ce nom, je n'arriverai pas à l'écrire correctement sans erreur de syntaxe, de surcroît le nom est complètement obscur...


- Non, on n'utilise pas la variable globals de cette façon, d'ailleurs on s'arrange pour éviter autant que possible les variables globales dans les fonctions.

De toute manière, j'ai bien compris que pour toi, c'est « parle à mon cul ma tête est malade ».

On ne va pas s'amuser à essayer de déchiffrer ton code (moi, non), réduis le au strict minimum, d'ailleurs sur internet, il y a plein d'exemples montrant comment lier scrollbar et canvas, c'est tout au plus une 20aine de lignes de code.

2
Phil_1857 Messages postés 1872 Date d'inscription lundi 23 mars 2020 Statut Membre Dernière intervention 28 février 2024 168
Modifié le 14 janv. 2023 à 17:01

Bonjour PCHICopat,

Bien répondu ! C'est vrai que c'est un peu ça ....  :-)

Et toutes ces lignes vides...

Et, pour la clarté, on l'a déjà dit:

les imports

puis les définitions de fonctions

puis les constantes

puis la création de la fenêtre et des widgets associés

0
Pr.Witherfire
14 janv. 2023 à 18:52

Bonjour.

Premièrement, c'est ma personnalité, ma logique, et il est difficile de la changer.

Deuxièmement, désolé d'être DEButant, et peut être DEBile.

Troisièmement, en tant que débutant, je m'attendais à un peu plus de patience de votre part. Être sur un forum, pour moi, c'est aider ceux qui ont des problèmes. Pas les rabaisser. Je suis conscient que je ne comprends pas forcément tout le temps vos remarques mais certaines choses restent sombres pour moi. Merci et au revoir quand même. J'espère ne pas avoir été agressif.

0
yg_be Messages postés 23487 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 mars 2025 1 570
15 janv. 2023 à 19:40

C'est précisément parce que nous voulons t'aider que nous réagissons ainsi.  Sinon, nous ignorerions simplement tes questions.

Nous te voyons faire des choix qui te compliquent la vie, te ralentissent, et, peut-être, te conduire ensuite à recommencer ton projet à zéro.

Pour t'aider, nous te suggérons donc régulièrement de revoir ces choix, d'utiliser des méthodes éprouvées.

Tu choisis de ne pas tenir compte des nos suggestions, et c'est ton droit.

Cependant, cela est un peu agaçant pour nous, cela nous donne l'impression de perdre notre temps, d'autant plus quand tu reviens avec un autre "problème" probablement causé, certainement plus compliqué à résoudre, par le fait que tu utilises tes propres méthodes, loin des bonnes pratiques du métier.

Je pense que personne, ici, ne souhaites te rabaisser.  Certains essaient de te ramener sur le chemin du conformisme.

Tu joues deux personnages.  D'un côté, le total non conformiste, qui fait ses propres choix envers et contre tout.  D'un autre côté, le débutant qui demande de l'aide.  Nous avons du mal à bien communiquer avec ces deux personnages.

De notre point de vue, tu te comportes un peu comme un bricoleur qui a décidé de ne travailler qu'avec un marteau.  Il vient demander de l'aide parce qu'il a un problème pour enfoncer ses vis.  Et il s'étonne du manque de patience des ses interlocuteurs.

1
Pr.Witherfire > yg_be Messages postés 23487 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 mars 2025
16 janv. 2023 à 17:51

Ok merci désolé. J'ai compris. Désolé.

PS: le choix de pseudo était au contraire très drôle. Mais est tu sur le forum sous un autre nom que je connais ?

Au revoir 

1
Phil_1857 Messages postés 1872 Date d'inscription lundi 23 mars 2020 Statut Membre Dernière intervention 28 février 2024 168 > Pr.Witherfire
Modifié le 17 janv. 2023 à 09:58

Bonjour,

Je ne te crois pas débile du tout mais personnellement, je pense ceci est plus lisible et facile à suivre:

# -*- coding:Utf-8 -*-

from tkinter import *

def ouvre(Cat):
    ''' Cette fonction crée des cadres des boutons qui ne commandent rien '''

    "bouton_"+str(Cat) = Button(fenetre, text= "<", font=(car_font,35), bg=color_1, fg=color_2, bd=0,height=1, command= lambda: PCHIFoFerDO(int(Cat)))

    if Cat == 1:
        "bouton_" + str(Cat).place(x=20, y=111)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="1", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=200)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="2", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=300)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="3", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=400)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="4", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=500)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="5", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=600)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="6", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=700)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="7", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=800)

        f2 = Frame(fenetre, bg=color_1, width=400, height=100)
        bouton_tuto = Button(f2, bg=color_1, text="8", font=(car_font, 25), fg=color_2, bd=0)
        bouton_tuto.place(x=160, y=10)
        f2.place(x=0, y=900)

    elif Cat == 2:
        "bouton_" + str(Cat).place(x=20, y=211)

    elif Cat == 3:
        "bouton_" + str(Cat).place(x=20, y=311)

color_2 = "Red"
color_1 = "Blue"
car_font = "Arial"

fenetre = Tk()
fenetre.title("Maths")
fenetre.geometry("1600x900+-8+0")

f1 = Frame(fenetre, width=500, height=500)
scroll_bar_1 = Scrollbar(f1, orient=VERTICAL)
scroll_bar_1.pack(side=RIGHT, fill=Y)

zone_graphique = Canvas(f1, width=400, height=900, bg=color_1)
zone_graphique.config(yscrollcommand=scroll_bar_1.set)
scroll_bar_1.config(command=zone_graphique.yview)

zone_graphique.create_line(0, 60, 400, 60, fill=color_2)
zone_graphique.create_line(0, 61, 400, 61, fill=color_2)
zone_graphique.create_line(0, 62, 400, 62, fill=color_2)

label_1 = Label(fenetre, text="Débutant", fg=color_2, bg=color_1, font=(car_font, 25))
label_1.place(x=200, y=125)
f1.place(x=0, y=0)

bouton_1 = Button(fenetre, text= "^", font=(car_font,35), bg=color_1, fg=color_2, bd=0,height=1, command= lambda : ouvre(1))
bouton_1.place(x=20, y=111)

scroll_bar_2 = Scrollbar(zone_graphique)
scroll_bar_2.place(x=375, y=0)

scroll_bar_2.config(command = zone_graphique.yview )
zone_graphique.place(x=0, y=0)

fenetre.mainloop()

Ceci dit, je te livre un petit texte que j'avais trouvé sur internet quand je faisais du C, mais après tout,

ça peut s'appliquer à n'importe quel langage :

.

" I would agree that it is not possible to compare the value of a program
layout with a real work of fine art such as a John Constable painting or
a Michaelangelo statue, I do think a well laid out and literate example of
programming is not only much easier to read and understand, but also it
does have a certain aesthetic appeal."

0

Salut Pr.Witherfire.

.

> Premièrement, c'est ma personnalité, ma logique, et il est difficile de la changer.

.

Bah si tu postes du code publiquement, il va le falloir, sinon, tu vas te prendre une « volée de bois vert » chaque fois, et encore là c'est gentillet, sur d'autres forums, cela aurait été plus cru.

.

.

> Deuxièmement, désolé d'être DEButant, et peut être DEBile.

.

Si tu es débutant, sans doute qu'il est bon d'écrire ton code comme la norme le conseille ! Non ? Personne n'a dit ici que tu étais débile... Mais que simplement tu n'appliquais pas ce que TOUT LE MONDE te reproche dans ton code, qui altère sa lisibilité et compréhension...

.

.

> Troisièmement, en tant que débutant, je m'attendais à un peu plus de patience de votre part. Être sur un forum, pour moi, c'est aider ceux qui ont des problèmes. Pas les rabaisser. Je suis conscient que je ne comprends pas forcément tout le temps vos remarques mais certaines choses restent sombres pour moi. Merci et au revoir quand même. J'espère ne pas avoir été agressif.

.

Inutile de faire ta vierge effarouchée, oui blabla t'es débutant, on l'a tous été, pour ma part lorsque j'ai débuté je ne m'égarais pas dans l'excentricité et encore moins dans des simagrées, je prenais bon conseil des gens un peu plus (beaucoup) plus expérimentés, puis dis-nous où ce qu'on t'a expliqué était difficile à comprendre ?

.

Alors que tu veuilles rester dans ta droiture et ne pas modifier ta façon de faire, libre à toi, mais alors ne t'offusques pas si on s'offusque verbalement de lire ce « brouhaha » de code, ce n'est pas pour t'ennuyer qu'il y a des conventions de codage.

.

.

La très réputée pep8 est à lire.
https://peps.python.org/pep-0008/
y a même des versions traduites dont une là.
https://www.codeflow.site/fr/article/python-pep8

.

ps: Navré du choix de pseudo, je n'avais pas pu m'en empêcher.

1
yg_be Messages postés 23487 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 mars 2025 Ambassadeur 1 570
14 janv. 2023 à 19:34

bonjour,

tu voudrais un scrollbar pour ta liste de 8 éléments?

0
Pr.Witherfire
15 janv. 2023 à 11:18

Oui. J'espere que c'est possible. J'ai cherché sur internet, copié les exemples, mais ça n'a pas marché dans mon contexte. C'est pour ca que je poste ici. Merci beaucoup.

0
yg_be Messages postés 23487 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 mars 2025 1 570 > Pr.Witherfire
15 janv. 2023 à 12:02

Tes 8 éléments ne sont pas dans un canvas, ce qui contredit la première phrase "Je voudrais "tout simplement" qu'une scrollbar fasse défiler un canvas".

0
Pr.Witherfire > yg_be Messages postés 23487 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 mars 2025
15 janv. 2023 à 13:54

Oui mais il y a des lignes (et je vais en rajouter) dans le canvas.

Merci

0
yg_be Messages postés 23487 Date d'inscription lundi 9 juin 2008 Statut Contributeur Dernière intervention 10 mars 2025 1 570 > Pr.Witherfire
15 janv. 2023 à 18:45

Partage alors un code qui contient un canevas que tu veux contrôler par scrollbar.

0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question

Allez, je suis bon joueur, un script rapide permettant d'ajuster le scroll en fonction de ce que contient le canvas.

.

Tu remarqueras qu'il n'y a pas vraiment besoin de commentaires, c'est relativement limpide et lisible, sans doute devras-tu te renseigner sur certaines méthodes de tkinter.

.

import tkinter as tk

# On définit quelques constantes !
WIDTH = 600
HEIGHT = 210

LINE_HEIGHT = 30
LINE_COLORS = 'grey', 'darkGrey'

SCROLL_WIDTH = 16


# Une fonction éphémère permettant d'ajouter une « ligne » au canvas
# avec une variable globale =)
line_number = 0

def add_line(canvas, text):
   global line_number
   y = LINE_HEIGHT * line_number
   background = LINE_COLORS[line_number % 2]
   canvas.create_rectangle(
      0, y, WIDTH, y + LINE_HEIGHT, fill=background, width=0,
   )
   canvas.create_text(10, y + LINE_HEIGHT / 2, text=text, anchor=tk.W,)
   line_number += 1
   # mise à jour de la zone de scroll du canvas
   canvas.configure(scrollregion=(0, 0, 0, line_number * LINE_HEIGHT))


window = tk.Tk()
window.resizable(False, False)

table = tk.Frame(window)
table.grid()

canvas = tk.Canvas(
   table,
   width=WIDTH,
   height=HEIGHT,
   highlightthickness=0,
   yscrollincrement=LINE_HEIGHT,
   bg='pink',
)
canvas.grid()

scroll_bar = tk.Scrollbar(
   table, width=SCROLL_WIDTH, orient=tk.VERTICAL, highlightthickness=0
)
scroll_bar.grid(row=0, column=1, sticky=tk.NSEW)

canvas.config(yscrollcommand=scroll_bar.set)
scroll_bar.config(command=canvas.yview)

for i in range(1, 25):
   add_line(canvas, f'ligne n°{i}')

canvas.mainloop()

.

A toi d'adapter à ton besoin.

0
Pr.Witherfire
16 janv. 2023 à 17:52

Ok merci beaucoup.

0