Je dois coder un petit programme pour avoir un bandeau avec deux couleurs en dégradé. Le problème c'est que je ne vois pas comment créer ce dégradé ?
Le code :
# -*- coding : utf-8 -*-
def dec2hex(nd) :
"""Transformation décimal --> hexadécimal"""
hexa = ""
symboles = "0123456789ABCDEF"
while nd != 0 :
pos = int(nd) % 16 # on détermine pos en divisant le nombre par 16 (on ne prend pas le reste)
sym = symboles[pos] # on prend le symbole qui correspond à la position pos
hexa = sym + str(hexa) # on "actualise" le nombre hexadécimal
nd = int(nd) / 16 # on divise le nombre par 16 jusqu'à obtenir 0
if len(hexa) < 2 :
hexa += "0"
return hexa[1:]
def RVB2HTML(r, v, b) :
html = "#" # Création
html += dec2hex(r) # du
html += dec2hex(v) # code couleur
html += dec2hex(b) # HTML
return html
from tkinter import *
from random import *
fen = Tk() # Création de la fenêtre, avec options
fen.title("Dégradé de deux couleurs")
fen.geometry("300x80")
fen.resizable(width = False, height = False)
Canv = Canvas(fen, width = 296, height = 76, bg = 'white') # Création et placement du Canvas
Canv.place(x = 0, y = 0)
r = randint(0,255)
v = randint(0,255)
b = randint(0,255)
could = RVB2HTML(r, v, b) # couleur de départ
r2 = randint(0,255)
v2 = randint(0,255)
b2 = randint(0,255)
coulf = RVB2HTML(r2, v2, b2) # couleur finale
for i in range(297) :
Canv.create_line(i, 0, i, 77, fill = coul)
# c'est dans cette boucle que je dois créer le dégradé
fen.mainloop()
EDIT : pour ceux qui me diraient que ça ne sert à rien de créer une fonction qui convertit le décimal en hexadécimal parce que il y a des fonctions intégrées qui le font, c'est parce que c'était un de mes exercices de créer des fonctions pareilles. Et ça m'a permit de mieux comprendre le concept des nombres binaires et hexadécimaux
il faut être à l'aise, un minimum, en math. On va commencer par un exemple simple où on travaille en niveau de gris. Un niveau de gris est un nombre entre 0 et 255 (pour ressembler à ce que tu fais en couleur). Pour créer un dégradé il te faut quelques infos :
le niveau de départ
le niveau d'arrivée
le nombre d'étapes
l'étape courante
Si, par exemple, tu veux faire un dégradé du niveau 10 au niveau 120 en 10 étapes alors il te faut une fonction dégradé(niveau_debut, niveau_fin, nombre_étapes, i) qui te donne le niveau de gris à l'étape i. Tu sais déjà que dégradé(niveau_debut, niveau_fin, nombre_étapes, 0) vaut niveau_début, dégradé(niveau_debut, niveau_fin, nombre_étapes, nombre_étapes) vaut niveau_fin. Entre les deux tu fais une simple règle de trois pour avoir un dégradé linéaire … Sur l'exemple cela donnera 10 (étape 0), 21 (étape 1), 32,43,54,65,76,87,98,109,120 (étape 10).
Une fois que tu sais le faire avec un niveau de gris, tu sais le faire avec n'importe quelles couleurs définies par un triplet (R,V,B) en faisant le même dégradé par composantes.
Un truc simple que tu trouves aisément avec une recherche google …
First solve the problem. Then, write the code. ~ John Johnson
EDIT : pour ceux qui me diraient que ça ne sert à rien de créer une fonction qui convertit le décimal en hexadécimal c'est inutile parce que il y a des fonctions intégrées qui le font, c'est parce que c'était un de mes exercices de créer des fonctions pareilles. Et ça m'a permit de mieux comprendre le concept des nombres binaires et hexadécimaux
Je ne vois dans ton code aucune fonction qui « convertit le décimal en hexadécimal ».
Je ne vois dans ton code aucune fonction qui « convertit le décimal en hexadécimal ».
Lignes 3 à 14
@PicoDev :
Je vais regarder ça, merci !
EDIT : Par contre j'ai quelques fois, une TclError (invalid name color) parce qu'il n'y a pas assez de caractères dans la chaîne html (voir lignes 16 à 21). Il y a, pas tout le temps, 6 caractères au lieu de 7. J'avais rajouté
if len(hexa) < 2:
hexa += "0"
Pour arranger la chose, mais je ne comprends pas pourquoi je l'obtiens encore ?
Il s'agit plutôt là d'une fonction qui retourne la représentation hexadécimale d'un nombre, mais qui fonctionne mal (avec 0 en entrée par exemple).
C'est pas pareil ? Et pour son fonctionnement j'essaye de l'améliorer mais c'est assez compliqué.
entwanne a écrit:
Avec ton code, tu rajoutes un '0' à la fin de la représentation (pourquoi ?), puis tu supprimes le 1er caractère de la chaîne (pourquoi-bis ?).
Le zéro c'est parce que, dans mon énoncé, on disait : "Attention, le code HTML d'une couleur doit forcément compter 7 caractères (il faut ajouter des 0 le cas écchéant)"
Pour la suppression du premier caractère, quand j'avais fini la création de la fonction (dans le mien la dernière ligne était : "return hexa"), j'ai regardé la correction et la dernière ligne était "return hexa[1:]". Alors j'ai modifié la dernière ligne de ma fonction pour voir ce que ça donne mais ça ne changeait rien alors j'ai laissé ainsi.
J'ai trouvé ça en cherchant un peu (j'ai trouvé un des posts d'OC, c'est une réponse de nohar) :
def echelle(color_begin, color_end, n_vals):
r1, g1, b1 = color_begin
r2, g2, b2 = color_end
degrade = []
etendue = n_vals - 1
for i in range(n_vals):
alpha = 1 - i / etendue
beta = i / etendue
r = int(r1 * alpha + r2 * beta)
g = int(g1 * alpha + g2 * beta)
b = int(b1 * alpha + b2 * beta)
degrade.append((r, g, b))
return degrade
Elle reprend plus ou moins ce qu'a dit PicoDev, ais il y a quelques trucs que je ne comprends pas :
n_vals c'est le nombre d'étapes ?
puisqu'il met r1, g1, b1 = color_begin, et pareil pour color_end, ça veut dire que ces deux variables doivent contenir 3 variables (r,v et b) ? Du coup si dans ces deux paramètres de la fonction je met une liste, ça devrait donctionner ?
C'est pas pareil ? Et pour son fonctionnement j'essaye de l'améliorer mais c'est assez compliqué.
Pas vraiment, non, c'est comme la différence entre un nombre et une chaîne de caractères. À quoi as-tu droit pour réaliser cette fonction ? (je pense à str.format par exemple).
La fonction echelle que tu montres ici est plutôt simple, et reprend effectivement ce qu'a expliqué PicoDev. nb_vals correspond au nombre de couleurs à générer (le nombre de stops, donc) et etendue est l'amplitude de l'intervalle de valeurs.
alpha et beta sont les coefficients qui évoluent dans un sens et dans l'autre du dégradé (tu as toujours alpha + beta qui vaut 1).
color_begin et color_end sont des tuples de 3 éléments, ça fonctionnera aussi avec des listes.
Je ne comprends alors pas ton deuxième message (« pour ceux qui me diraient que ça ne sert à rien de créer une fonction qui convertit le décimal en hexadécimal […] »). Si tu as droit aux fonctions de la bibliothèque standard, utilise-les, elles ne sont pas boguées.
I-Scryper a écrit:
Et que signifie "L'amplitude de l'intervalle des valeurs" ?
Je ne comprends alors pas ton deuxième message (« pour ceux qui me diraient que ça ne sert à rien de créer une fonction qui convertit le décimal en hexadécimal […] »). Si tu as droit aux fonctions de la bibliothèque standard, utilise-les, elles ne sont pas boguées.
Parce que un de mes exercices était de créer des fonctions qui convertissent de l'hexa au binaire et au décimal, du binaire en hexa et en décimal, etc...
Et vu que j'ai passé du temps à les faire, je les utilises.
J'ai créé la fonction, et je l'ai modifié pour qu'elle agisse directement sur le Canvas. Le problème c'est que rien ne se dessine sur le Canvas (il garde sa couleur d'origine).
La fonction :
def degrade(couldepart_tuple, coulfinale_tuple, etapes) :
global Canv
rd, vd, bd = couldepart_tuple
rf, vf, bf = coulfinale_tuple
etendue = etapes - 1
for i in range(etapes) :
alpha = 1 - i / etendue
beta = i / etendue
r = int(rd * alpha + rf * beta)
v = int(vd * alpha + vf * beta)
b = int(bd * alpha + bf * beta)
coul = RVB2HTML(r, v, b)
Canv.create_line(x1, 0, x2, 78, fill = coul)
x1 += 1
x2 += 1
return degrade
Pourquoi ta fonction degrade se retourne elle-même ?
Et peux-tu être plus explicite que « ça ne fonctionne toujours pas » ?
Sinon, je viens de tester chez moi, en remplaçant ta fonction RVB2HTML par un équivalent non bogué (comme je te le fais remarquer depuis quelques messages, à base de str.format), la fonction de dégradé fonctionne bien.
Il faut voir aussi quelle valeur tu donnes au 3ème paramètre de degrade. J'ai mis 296 pour correspondre à la largeur de ton canevas.
Pourquoi ta fonction degradese retourne elle-même ?
Elle ne se retourne pas elle-même, j'ai mal recopié. Normalement c'est une liste mais la liste était présente seulement dans le code de nohar que j'avais trouvé en cherchant sur OC.
entwanne a écrit:
Et peux-tu être plus explicite que « ça ne fonctionne toujours pas » ?
Le Canvas reste blanc. Il n'y a rien qui se dessine.
entwanne a écrit:
Sinon, je viens de tester chez moi, en remplaçant ta fonction RVB2HTML par un équivalent non bogué (comme je te le fais remarquer depuis quelques messages, à base de str.format), la fonction de dégradé fonctionne bien.
Laquelle ? Ainsi je peux améliorer ma fonction.
entwanne a écrit:
Il faut voir aussi quelle valeur tu donnes au 3ème paramètre de degrade. J'ai mis 296 pour correspondre à la largeur de ton canevas.
Moi aussi j'ai juste mis :
nb_etapes = Canv.cget('width')
Mais ça revient quand même à 296.
Merci !
EDIT : Je viens de mettre 'return coul', et ça fonctionne parfaitement. Le dégradé est présent sur le Canvas.
Elle ne se retourne pas elle-même, j'ai mal recopié. Normalement c'est une liste mais la liste était présente seulement dans le code de nohar que j'avais trouvé en cherchant sur OC.
Mais pourquoi a-t-elle besoin de retourner quelque chose ?
I-Scryper a écrit:
Laquelle ? Ainsi je peux améliorer ma fonction.
Ta fonction dec2hex, en plus d'avoir un nom inapproprié, ne marche pas. C'est elle qui me générait un code couleur invalide, et donc faisait planter le programme quand j'essayais un dégradé entre (0, 0, 0) et (255, 255, 255).
Regarde ce que retourne RVB2HTML(0, 0, 0) par exemple…
I-Scryper a écrit:
EDIT : Je viens de mettre 'return coul', et ça fonctionne parfaitement. Le dégradé est présent sur le Canvas.
Je pense que tu as fait d'autres corrections en même temps. La valeur de retour de la fonction degrade n'a aucune raison de changer quoi que ce soit.
Elle ne se retourne pas elle-même, j'ai mal recopié. Normalement c'est une liste mais la liste était présente seulement dans le code de nohar que j'avais trouvé en cherchant sur OC.
Mais pourquoi a-t-elle besoin de retourner quelque chose ?
On peut créer des fonctions qui ne retournent rien ?
entwanne a écrit:
I-Scryper a écrit:
Laquelle ? Ainsi je peux améliorer ma fonction.
Ta fonction dec2hex, en plus d'avoir un nom inapproprié, ne marche pas. C'est elle qui me générait un code couleur invalide, et donc faisait planter le programme quand j'essayais un dégradé entre (0, 0, 0) et (255, 255, 255). Regarde ce que retourne RVB2HTML(0, 0, 0) par exemple…
Un nom inapproprié ? Pourtant elle convertit bien le décimal en hexadécimal. Je sais que c'est celle là qui pose problème, je voulais dire le nom de la fonction que tu utilises ainsi je peux, par rapport à celle là, améliorer la mienne.
On peut créer des fonctions qui ne retournent rien ?
Pas exactement. Tu peux créer une fonction sans return, et la fonction retournera None.
I-Scryper a écrit:
Un nom inapproprié ? Pourtant elle convertit bien le décimal en hexadécimal. Je sais que c'est celle là qui pose problème, je voulais dire le nom de la fonction que tu utilises ainsi je peux, par rapport à celle là, améliorer la mienne.
Oui, un nom inapproprié. Si j'appelle dec2hex(0xFF), où vois-tu une « conversion du décimal vers l'hexadécimal » ?
Comme je l'ai indiqué, j'ai utilisé str.format à la place, avec les flags dédiés (0, 2 et x).
× Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
× Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique
entwanne — @entwanne — Un zeste de Python — La POO en Python — Notions de Python avancées — Les secrets d'un code pythonique