使用 Python 生成驗證碼(CAPTCHA)
阿新 • • 發佈:2018-12-11
CAPTCHA 影象
Python 資料視覺化程式設計實戰程式碼
點選檢視詳細內容
from PIL import Image, ImageDraw, ImageFont import random import string class SimpleCaptchaException(Exception): pass class SimpleCaptcha(object): def __init__(self, length=5, size=(200, 100), fontsize=36, random_text=None, random_bgcolor=None): self.size = size self.text = "CAPTCHA" self.fontsize = fontsize self.bgcolor = 255 self.length = length self.image = None # current captcha image if random_text: self.text = self._random_text() if random_bgcolor: self.bgcolor = self._random_color() if not self.text: raise SimpleCaptchaException("Field text must not be empty.") if not self.size: raise SimpleCaptchaException("Size must not be empty.") if not self.fontsize: raise SimpleCaptchaException("Font size must be defined.") def _center_coords(self, draw, font): width, height = draw.textsize(self.text, font) xy = (self.size[0] - width) / 2., (self.size[1] - height) / 2. return xy def _add_noise_dots(self, draw): size = self.image.size for _ in range(int(size[0] * size[1] * 0.1)): draw.point((random.randint(0, size[0]), random.randint(0, size[1])), fill="white") return draw def _add_noise_lines(self, draw): size = self.image.size for _ in range(8): width = random.randint(1, 2) start = (0, random.randint(0, size[1] - 1)) end = (size[0], random.randint(0, size[1] - 1)) draw.line([start, end], fill="white", width=width) for _ in range(8): start = (-50, -50) end = (size[0] + 10, random.randint(0, size[1] + 10)) draw.arc(start + end, 0, 360, fill="white") return draw def get_captcha(self, size=None, text=None, bgcolor=None): if text is not None: self.text = text if size is not None: self.size = size if bgcolor is not None: self.bgcolor = bgcolor self.image = Image.new('RGB', self.size, self.bgcolor) font = ImageFont.truetype('arial.ttf', self.fontsize) draw = ImageDraw.Draw(self.image) xy = self._center_coords(draw, font) draw.text(xy=xy, text=self.text, font=font) # Add some dot noise draw = self._add_noise_dots(draw) # Add some random lines draw = self._add_noise_lines(draw) # self.image.show() display(self.image) return self.image, self.text def _random_text(self): letters = string.ascii_lowercase + string.ascii_uppercase random_text = "" for _ in range(self.length): random_text += random.choice(letters) return random_text def _random_color(self): r = random.randint(0, 255) g = random.randint(0, 255) b = random.randint(0, 255) return (r, g, b) sc = SimpleCaptcha(length=6, fontsize=36, random_text=True, random_bgcolor=True) sc.get_captcha()