1. 程式人生 > 實用技巧 >Python實現畫圖軟體功能

Python實現畫圖軟體功能

概述

雖然Python的強項在人工智慧,資料處理方面,但是對於日常簡單的應用,Python也提供了非常友好的支援(如:Tkinter),本文主要一個簡單的畫圖小軟體,簡述Python在GUI(圖形使用者介面)方面的應用,僅供學習分享使用,如有不足之處,還請指正。

設計思路

  • 頁面佈局:主要分為上下兩部分 a. 繪圖區域,本例以Canvas實現 b. 下部:功能區,由按鈕實現
  • 事件監聽:通過給功能按鈕繫結事件,來實現不同的功能,如:繪線,繪矩形等功能。
  • 繪圖區域:監聽滑鼠左鍵的按下(開始繪圖)和抬起(停止繪圖),再根據不同的按鈕實現繪製不同的圖形。

涉及知識點

  • 開發工具:Python3.7 , PyCharm2019
  • Tkinter 是 Python 的標準 GUI 庫。Python 使用 Tkinter 可以快速的建立 GUI 應用程式。
  • Canvas控制元件提供了一個自定義的繪圖區域,可以通過不同的函式來繪製不同的圖形。
    • 繪製直線 create_line(self.x, self.y, event.x, event.y, fill=self.fgcolor)
    • 繪製帶箭頭的直線 create_line(self.x, self.y, event.x, event.y, arrow=LAST, fill=self.fgcolor)
    • 繪製矩形 create_rectangle(self.x, self.y, event.x, event.y, outline=self.fgcolor)
    • 繪製曲線,是通過繪製不同的點來實現的
    • 清除圖形 drawpad.delete('all')
  • Button 按鈕控制元件,通過繫結(bind)不同的監聽事件來實現不同的功能。
    • name屬性設定按鈕的名稱,
    • text屬性設定按鈕的顯示文字。
    • bind 繫結事件

示例效果圖

本例主要實現繪製直線,帶箭頭的直線,曲線,矩形,清除等功能,如下所示:

核心程式碼

在本例中,主要功能如下:

建立畫板

1 """建立畫圖區域"""
2 self.drawpad = Canvas(self, width=win_width, height=win_height, bg=bgcolor)
3 self.drawpad.pack()
View Code

建立按鈕

 1        # 建立按鈕
 2         self.btn_start = Button(self, name='start', text='開始')
 3         self.btn_start.pack(side='left', padx=10)
 4         self.btn_pen = Button(self, name='pen', text='畫筆')
 5         self.btn_pen.pack(side='left', padx=10)
 6         self.btn_rect = Button(self, name='rect', text='矩形')
 7         self.btn_rect.pack(side='left', padx=10)
 8         self.btn_clear = Button(self, name='clear', text='清屏')
 9         self.btn_clear.pack(side='left', padx=10)
10         self.btn_erasor = Button(self, name='erasor', text='橡皮擦')
11         self.btn_erasor.pack(side='left', padx=10)
12         self.btn_line = Button(self, name='line', text='直線')
13         self.btn_line.pack(side='left', padx=10)
14         self.btn_line_arrow = Button(self, name='line_arrow', text='箭頭直線')
15         self.btn_line_arrow.pack(side='left', padx=10)
16         self.btn_color = Button(self, name='color', text='顏色')
17         self.btn_color.pack(side='left', padx=10)
View Code

繫結事件

1        # 繫結事件
2         self.btn_line.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
3         self.btn_line_arrow.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
4         self.btn_rect.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
5         self.btn_pen.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
6         self.btn_erasor.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
7         self.btn_clear.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
8         self.btn_color.bind('<Button-1>', self.eventManager)  # 點選按鈕事件
View Code

功能實現

 1    def eventManager(self, event):
 2         name = event.widget.winfo_name()
 3         print(name)
 4         self.start_flag = True
 5         if name == 'line':
 6             # 左鍵拖動
 7             self.drawpad.bind('<B1-Motion>', self.myline)
 8         elif name == 'line_arrow':
 9             self.drawpad.bind('<B1-Motion>', self.myline_arrow)
10         elif name == 'rect':
11             self.drawpad.bind('<B1-Motion>', self.myrect)
12         elif name == 'pen':
13             self.drawpad.bind('<B1-Motion>', self.mypen)
14         elif name == 'erasor':
15             self.drawpad.bind('<B1-Motion>', self.myerasor)
16         elif name == 'clear':
17             self.drawpad.delete('all')
18         elif name == 'color':
19             c = askcolor(color=self.fgcolor, title='請選擇顏色')
20             print(c)  # c的值 ((128.5, 255.99609375, 0.0), '#80ff00')
21             self.fgcolor = c[1]
22 
23     def startDraw(self, event):
24         self.drawpad.delete(self.lastdraw)
25         if self.start_flag:
26             self.start_flag = False
27             self.x = event.x
28             self.y = event.y
29 
30     def stopDraw(self, event):
31         self.start_flag = True
32         self.lastdraw = 0
33 
34     def myline(self, event):
35         self.startDraw(event)
36         self.lastdraw = self.drawpad.create_line(self.x, self.y, event.x, event.y, fill=self.fgcolor)
37 
38     def myline_arrow(self, event):
39         self.startDraw(event)
40         self.lastdraw = self.drawpad.create_line(self.x, self.y, event.x, event.y, arrow=LAST, fill=self.fgcolor)
41 
42     def myrect(self, event):
43         self.startDraw(event)
44         self.lastdraw = self.drawpad.create_rectangle(self.x, self.y, event.x, event.y, outline=self.fgcolor)
45 
46     def mypen(self, event):
47         self.startDraw(event)
48         print('self.x=', self.x, ',self.y=', self.y)
49         self.drawpad.create_line(self.x, self.y, event.x, event.y, fill=self.fgcolor)
50         self.x = event.x
51         self.y = event.y
52 
53     def myerasor(self, event):
54         self.startDraw(event)
55         print('self.x=', self.x, ',self.y=', self.y)
56         self.drawpad.create_rectangle(event.x - 3, event.y - 3, event.x + 3, event.y + 3, fill=bgcolor)
57         self.x = event.x
58         self.y = event.y
View Code

快捷鍵的實現

1  self.master.bind('<KeyPress-r>', self.hotKey)  # 繫結快捷鍵
2 self.master.bind('<KeyPress-g>', self.hotKey)  # 繫結快捷鍵
3 self.master.bind('<KeyPress-b>', self.hotKey)  # 繫結快捷鍵
4 self.master.bind('<KeyPress-y>', self.hotKey)  # 繫結快捷鍵
5 self.drawpad.bind('<ButtonRelease-1>', self.stopDraw)  # 左鍵釋放按鈕
View Code

快捷鍵功能實現

 1     def hotKey(self, event):
 2         c = event.char
 3         if c == 'r':
 4             self.fgcolor = 'red'
 5         elif c == 'g':
 6             self.fgcolor = 'green'
 7         elif c == 'b':
 8             self.fgcolor = 'blue'
 9         elif c == 'y':
10             self.fgcolor = 'yellow'
View Code

有需要的朋友,可點選連結下載整體程式碼,如下所示:

原始碼連結

備註

不積跬步,無以至千里;不積小流,無以成江海;鍥而舍之,朽木不折,鍥而不捨,金石可鏤。