小言_互联网的博客

Python图形处理

260人阅读  评论(0)

一、Pillow

PIL:Python Imaging Library,已经是Python平台事实上的图像处理标准库了。PIL功能非常强大,但API却非常简单易用。

由于PIL仅支持到Python 2.7,加上年久失修,于是一群志愿者在PIL的基础上创建了兼容的版本,名字叫Pillow,支持最新Python 3.x,又加入了许多新特性,因此,我们可以直接安装使用Pillow。

安装Pillow

如果安装了Anaconda,Pillow就已经可用了。否则,需要在命令行下通过pip安装:

$ pip install pillow

如果遇到Permission denied安装失败,请加上sudo重试。

操作图像

来看看最常见的图像缩放操作,只需三四行代码:


  
  1. from PIL import Image
  2. # 打开一个jpg图像文件,注意是当前路径:
  3. im = Image.open( 'test.jpg')
  4. # 获得图像尺寸:
  5. w, h = im.size
  6. print( 'Original image size: %sx%s' % (w, h))
  7. # 缩放到50%:
  8. im.thumbnail((w //2, h// 2))
  9. print( 'Resize image to: %sx%s' % (w //2, h// 2))
  10. # 把缩放后的图像用jpeg格式保存:
  11. im.save( 'thumbnail.jpg', 'jpeg')

其他功能如切片、旋转、滤镜、输出文字、调色板等一应俱全。

比如,模糊效果也只需几行代码:


  
  1. from PIL import Image, ImageFilter
  2. # 打开一个jpg图像文件,注意是当前路径:
  3. im = Image. open( 'test.jpg')
  4. # 应用模糊滤镜:
  5. im2 = im. filter(ImageFilter.BLUR)
  6. im2.save( 'blur.jpg', 'jpeg')

效果如下:

PIL的ImageDraw提供了一系列绘图方法,让我们可以直接绘图。比如要生成字母验证码图片:


  
  1. from PIL import Image, ImageDraw, ImageFont, ImageFilter
  2. import random
  3. # 随机字母:
  4. def rndChar():
  5. return chr(random. randint( 65, 90))
  6. # 随机颜色 1:
  7. def rndColor():
  8. return (random. randint( 64, 255), random. randint( 64, 255), random. randint( 64, 255))
  9. # 随机颜色 2:
  10. def rndColor2():
  11. return (random. randint( 32, 127), random. randint( 32, 127), random. randint( 32, 127))
  12. # 240 x 60:
  13. width = 60 * 4
  14. height = 60
  15. image = Image. new( 'RGB', (width, height), ( 255, 255, 255))
  16. # 创建Font对象:
  17. font = ImageFont. truetype( 'Arial.ttf', 36)
  18. # 创建Draw对象:
  19. draw = ImageDraw. Draw(image)
  20. # 填充每个像素:
  21. for x in range(width):
  22. for y in range(height):
  23. draw. point((x, y), fill= rndColor())
  24. # 输出文字:
  25. for t in range( 4):
  26. draw. text(( 60 * t + 10, 10), rndChar(), font=font, fill= rndColor2())
  27. # 模糊:
  28. image = image. filter(ImageFilter.BLUR)
  29. image. save( 'code.jpg', 'jpeg')

我们用随机颜色填充背景,再画上文字,最后对图像进行模糊,得到验证码图片如下:

 

如果运行的时候报错:

IOError: cannot open resource

这是因为PIL无法定位到字体文件的位置,可以根据操作系统提供绝对路径,比如:

'/Library/Fonts/Arial.ttf'

要详细了解PIL的强大功能,请请参考Pillow官方文档:

Pillow (PIL Fork) 9.2.0 documentation

总结:

PIL提供了操作图像的强大功能,可以通过简单的代码完成复杂的图像处理。

二、海龟绘图 

在1966年,Seymour Papert和Wally Feurzig发明了一种专门给儿童学习编程的语言——LOGO语言,它的特色就是通过编程指挥一个小海龟(turtle)在屏幕上绘图。

海龟绘图(Turtle Graphics)后来被移植到各种高级语言中,Python内置了turtle库,基本上100%复制了原始的Turtle Graphics的所有功能。

我们来看一个指挥小海龟绘制一个长方形的简单代码:


  
  1. # 导入turtle包的所有内容:
  2. from turtle import *
  3. # 设置笔刷宽度:
  4. width( 4)
  5. # 前进:
  6. forward( 200)
  7. # 右转 90度:
  8. right( 90)
  9. # 笔刷颜色:
  10. pencolor( 'red')
  11. forward( 100)
  12. right( 90)
  13. pencolor( 'green')
  14. forward( 200)
  15. right( 90)
  16. pencolor( 'blue')
  17. forward( 100)
  18. right( 90)
  19. # 调用 done()使得窗口等待被关闭,否则将立刻关闭窗口:
  20. done()

在命令行运行上述代码,会自动弹出一个绘图窗口,然后绘制出一个长方形:

从程序代码可以看出,海龟绘图就是指挥海龟前进、转向,海龟移动的轨迹就是绘制的线条。要绘制一个长方形,只需要让海龟前进、右转90度,反复4次。

调用width()函数可以设置笔刷宽度,调用pencolor()函数可以设置颜色。更多操作请参考turtle库的说明。

绘图完成后,记得调用done()函数,让窗口进入消息循环,等待被关闭。否则,由于Python进程会立刻结束,将导致窗口被立刻关闭。

turtle包本身只是一个绘图库,但是配合Python代码,就可以绘制各种复杂的图形。例如,通过循环绘制5个五角星:


  
  1. from turtle import *
  2. def drawStar(x, y):
  3. pu()
  4. goto(x, y)
  5. pd()
  6. # set heading: 0
  7. seth( 0)
  8. for i in range( 5):
  9. fd( 40)
  10. rt( 144)
  11. for x in range( 0, 250, 50):
  12. drawStar(x, 0)
  13. done()

程序执行效果如下:

 

使用递归,可以绘制出非常复杂的图形。例如,下面的代码可以绘制一棵分型树:


  
  1. from turtle import *
  2. # 设置色彩模式是RGB:
  3. colormode( 255)
  4. lt( 90)
  5. lv = 14
  6. l = 120
  7. s = 45
  8. width(lv)
  9. # 初始化RGB颜色:
  10. r = 0
  11. g = 0
  12. b = 0
  13. pencolor(r, g, b)
  14. penup()
  15. bk(l)
  16. pendown()
  17. fd(l)
  18. def draw_tree(l, level):
  19. global r, g, b
  20. # save the current pen width
  21. w = width()
  22. # narrow the pen width
  23. width(w * 3.0 / 4.0)
  24. # set color:
  25. r = r + 1
  26. g = g + 2
  27. b = b + 3
  28. pencolor(r % 200, g % 200, b % 200)
  29. l = 3.0 / 4.0 * l
  30. lt(s)
  31. fd(l)
  32. if level < lv:
  33. draw_tree(l, level + 1)
  34. bk(l)
  35. rt( 2 * s)
  36. fd(l)
  37. if level < lv:
  38. draw_tree(l, level + 1)
  39. bk(l)
  40. lt(s)
  41. # restore the previous pen width
  42. width(w)
  43. speed( "fastest")
  44. draw_tree(l, 4)
  45. done()

执行上述程序需要花费一定的时间,最后的效果如下:

 


转载:https://blog.csdn.net/qq_35029061/article/details/127356389
查看评论
* 以上用户言论只代表其个人观点,不代表本网站的观点或立场