2010-11-18 29 views
4

J'utilise les modes PIL et Image en Python. Je veux créer une image avec ce code:Boucle Python pour module image et pil

imagesize = (12,12) 
image = Image.new("RGB",imagesize,color=None) 

Je vais utiliser cette fonction pour mettre pixels sur mon image:

.putpixel(xy, color) 

couleur est dans une liste de tuples. Pour exemple:

RGB = [((255, 255, 255),(207, 103, 36),(204, 93, 21),(204, 93, 21),(204, 93, 21), (.......some more RGB tuples.....)] 

je besoin d'une boucle qui en .putpixel (xy, couleur):

couleur est incrémenté d'un pas à chaque fois. Par exemple RGB [0], la prochaine boucle RGB [1] et ainsi de suite. Pendant que cette boucle est en cours, le x et le y sont les plus difficiles. x va de 1 à 12 (taille de l'image) alors que y est 0 et ensuite, quand x atteint imageize, il revient à 1 à 12 mais y est maintenant 1. La boucle est terminée lorsque x et atteignent la fin de la taille de l'image.

Quelqu'un peut-il m'aider? Je suis nouveau en Python.

Cordialement,

Favolas

EDIT

P: S - Vous avez oublié de dire que puisque c'est pour un projet scolaire, je ne peux pas utiliser des méthodes en dehors img.new, img.show et img.outpixel

+1

Sur un sidenote, putpixel est habituellement très lent. Vous voulez probablement utiliser putdata à la place, en définissant les données d'image en une seule fois. –

+0

Il ne semble pas que vous ayez fait _any_ tenter de résoudre cela vous-même ... – martineau

Répondre

2

Ok, mon commentaire d'en haut aurait vraiment dû être une réponse. Je devrais attraper un peu de sommeil. Vous pouvez simplement mettre vos données de pixels dans l'image à la fois. La méthode putdata d'un PIL.Image accepte une liste de tuples qui composent les pixels des images. Alors:

img = PIL.Image.new("RGB", (12, 12)) 
img.show() # see a black image 
pixels = [(255,0,0)]*(12*12) 
img.putdata(pixels) 
img.show() # see a red image 
+1

Ceci est pour un projet d'école et je ne peux pas utiliser de méthodes à côté de img.new, img.show et img.putpixel :) – Favolas

1

Cela dépend de la façon dont vous voulez mettre les couleurs RVB. Par exemple:

for y in range(12): 
    for x in range(12): 
    img.putpixel(x, y, RGB[(x + 12*y)%len(RBG)] 

mettra 0 à N couleurs RBG en 0 à N pixels, 0 à N RGBs à 0 + N, pixels 2N et ainsi de suite. Il y a un autre choix - choisir la couleur au hasard:

import random 
... 
for y in range(12): 
    for x in range(12): 
    img.putpixel(x, y, RBG[random.randint(0, len(RGB)-1)] 

Optimisation pour les deux cas est laissée en exercice.

+1

Salut.Merci pour votre réponse. Mais il me donne cette erreur: Traceback (dernier appel dernier): Fichier "", ligne 48, en ZeroDivisionError: division entière ou modulo par zéro – Favolas

+1

Merci @Favolas, corrigé. '(x + 12 * y)% len (RGB)' – khachik

1

Si vous avez des boucles imbriquées, i de 0 à 11 et j de 0 à 11, puis à indexer progressivement dans un vecteur unidimensionnel vous devez obtenir X [j + i * 11].

>>> for i in range(5): 
... for j in range(5): 
...  print j + i*5 

imprimera 0 à 24.

Voir d'autres réponses de meilleures façons de remplir les images, et il y a probablement des moyens plus pythonique de faire cela aussi. Mais ceci est la réponse générique!

Notez que ceci est pour les variables qui commencent à ZÉRO, pas UN. Pour votre image 12 x 12 pixels, la plage xy valide est comprise entre 0 et 11.

1

Si nous avons ces deux listes:

xy = [(1,2),(3,4),(5,6),(7,8)] 
rgb = [(0,0,255), (0,255,0), (255,0,0), (255,255,0), (255,255,255)] 

Nous pouvons cartographier la liste XY à la liste RVB dans un dictionnaire:

d = dict(zip(xy,rgb)) 

Ce qui ressemble à ceci:

>>> print(d) 
{(1, 2): (0, 0, 255), (5, 6): (255, 0, 0), (3, 4): (0, 255, 0), (7, 8): (255, 255, 0)} 

Nous avons maintenant un dictionnaire, la clé est le XY et la valeur est le RVB correspondant. Maintenant, nous pouvons cartographier ces paires clé-valeur en utilisant list comprehension:

[putpixel(x,col) for x,col in d.items()] 

Comme un test, une méthode putpixel() maquette qui imprime les entrées vérifier les résultats:

def putpixel(xy,col): 
    print('%s set to %s' % (xy,col)) 

>>> result = [putpixel(x,col) for x,col in d.items()] 
(1, 2) set to (0, 0, 255) 
(5, 6) set to (255, 0, 0) 
(3, 4) set to (0, 255, 0) 
(7, 8) set to (255, 255, 0) 

Liste compréhension renvoie généralement une liste des éléments traités, dans ce cas nous ne renvoyons pas un résultat de putpixel(), ainsi notre liste de résultats contiendrait des vides.