Tk畫板,使用Canvas控件製作
0.0展示:
0.1需要的控件:
直接白嫖代碼看最後面
依然使用tkinter模塊製作,你細細的品發現Tk能做的東西真多,繪圖首先需要畫布,這個東東就是動畫,需要Canvas創建
1 引入
需要askcolor函數,所以進一步簡化引入
from tkinter import *
from tkinter.colorchooser import *
2 需要一個全局變量
choosecolor = "black" #畫筆的顏色
3 創建窗體
基礎框架搭建
tk = Tk()
tk.title("Canvas Paint 1.1.3")
tk.mainloop()
4 控件
前三個好像都是廢話,一句一句的講沒必要,直接上控件,七零八碎到最後看看得了
4.1 詢問顏色控件
實現如下
先整一個框架存儲這一行
cco = Frame(tk, relief=SUNKEN)
cco.pack(pady=5)
展示框:
tmplb1 = Label(cco, text="展示:") #臨時文本
showLab = Label(cco, width=15, relief=GROOVE, bg="white") # 展示框初始化背景爲白
tmplb1.pack(side=LEFT) #佈局從左往右
showLab.pack(padx=10, side=LEFT) #佈局從左往右
輸入框,輸入顏色名和十六進制:
tmplb2 = Label(cco, text="可輸入[#十六進制]和[顏色名] : string") #臨時文本
tmplb2.pack(side=LEFT)
getc = Entry(cco, width=30) #設置文本框
getc.pack(side=LEFT)
後面的兩個按鈕:
cokbtn = Button(cco, text="確認", command=sure)
getc.bind("<Return>", sure_fun)
cokbtn.pack(side=LEFT, ipadx=3, ipady=3)
askbtn = Button(cco, text="使用Ask", command=usingAsk)
askbtn.pack(side=RIGHT, ipadx=3, ipady=3)
command參數是點擊按鈕調用哪個函數,這些函數後面再講
bind是綁定鍵位,在輸入框中按下回車可以觸發函數,如果報錯,見Python專欄中的另一篇文章解決
4.2 列表框和橡皮控件
其中橡皮是一個按鈕,初始化是沒有邊框的,按下出現邊框,再次按下沒有邊框
定義optionmenu列表:
Omf = Frame(tk) #定義框架
Omf.pack() #佈局框架
tmplb3 = Label(Omf, text="選擇畫筆寬度") #臨時文本
tmplb3.pack(side=LEFT) #佈局臨時文本
sizevar = IntVar() #在列表上的內容
SizeList = [x for x in range(20, 90, 6)] #列表值,用列表存儲
showoutput(SizeList) #臨時函數,可刪除
sizevar.set(SizeList[0]) #設置爲第一項
ShowOption = OptionMenu(Omf, sizevar, *SizeList) #框架,表面值,列表值
ShowOption.pack(side=LEFT) #佈局
橡皮按鈕:
eraser = Button(Omf, text="橡皮", relief=FLAT, command=erase)
eraser.pack(side=LEFT, ipadx=20, padx=50)
relief=FLAT
是無邊框
4.3 畫布和清除所有按鈕控件
畫布定義沒什麼難的
canvas = Canvas(tk, width=640, height=300)
#width是畫布寬度,height是高
canvas.pack(expand=True, fill=BOTH) #可以填充
加入清除所有按鈕
btn = Button(tk, text="清除所有", command=cls)
btn.pack(pady=5)
4.4 綁定畫布繪製
如果鼠標按下且在畫布上滑動,就觸發繪圖函數
canvas.bind("<B1-Motion>", paint)
5 各個函數
5.1 輸入框選取顏色函數
def sure():
global choosecolor
choosecolor = getc.get()
showLab.config(bg=choosecolor)
def sure_fun(self):
sure()
將輸入框的文本getc.get()
讀取,將全局變量賦值,再將展示框賦值,綁定的回車先調用sure_fun,再調用sure
5.2 使用askcolor
def usingAsk():
global choosecolor
myColor = askcolor()
choosecolor = myColor[1]
showLab.config(bg=choosecolor)
getc.delete(0, END)
getc.insert(0, myColor[1])
全局choosecolor,將askcolor函數返回的列表存入myColor,順便說返回值是一個列表,你可以加一句print輸出myColor,發現[0]是一個精確到小數好幾位的RGB,[1]是十六進制碼,所以我們需要[1]的值,更改展示框、輸入框重新放入十六進制。
5.3 橡皮函數
def erase():
global dercnt
global choosecolor
global tmpcolor
if dercnt == 0:
eraser.config(relief=RAISED)
tmpcolor = choosecolor
choosecolor = "#F0F0F0"
dercnt += 1
else:
eraser.config(relief=FLAT)
choosecolor = tmpcolor
dercnt -= 1
沒什麼技巧,用截屏軟件發現界面的背景是#F0F0F0,所以觸發橡皮就賦值顏色爲#F0F0F0,有一個變量叫做dercnt,如果是0,就說明當前不是橡皮,更改邊框,記錄臨時顏色,如果爲1,說明當前是橡皮,更改邊框,獲取上一次的顏色
5.4 繪圖
def paint(event):
YourChooseSize = sizevar.get()
x1, y1 = (event.x, event.y)
x2, y2 = (event.x+YourChooseSize, event.y+YourChooseSize)
canvas.create_oval(x1, y1, x2, y2, fill=choosecolor, outline=choosecolor)
獲取你選中的畫筆寬度,然後確定座標,畫圓,圓連起來不就是線嘛,單個的圓是這樣的
5.5 清除所有
def cls():
global choosecolor
getc.delete(0, END)
showLab.config(bg="white")
choosecolor = "black"
canvas.delete("all")
畫布delete所有,輸入框清除所有,初始顏色變成黑色,展示框變成白色
END 拿來代碼試試吧
所有代碼,Github上也有,https://github.com/Github-Programer
建議命名爲.pyw文件,是python的窗體文件,沒有控制檯
'''
@Author: Wyh
@Date: 2020-06-18 15:08:01
@LastEditTime: 2020-06-19 17:28:42
@LastEditors: Please set LastEditors
@Description: Canvas
@FilePath: \Coding-Notes\Python-Notes\圖形界面開發學習筆記\PythonGUI設計tkinter菜鳥編程書\Canvas畫板.pyw
@Version:
@1.0.0: 基礎構建繪圖面板
@1.1.0: 加入顏色
@1.1.1: 可設置十六進制顏色
@1.1.2: 可設置RGB
@1.1.3: 可設置顏色名
@1.2.0: 可設置畫筆寬度
@1.3.0: 繪製圖形
'''
from tkinter import *
from tkinter.colorchooser import *
dercnt = 0
def showoutput(LS): #測試函數,可以不要,但是記得修改調用部分
for i in LS:
print(i)
print(type(LS))
print(type(LS[0]))
def usingAsk():
global choosecolor
myColor = askcolor()
choosecolor = myColor[1]
showLab.config(bg=choosecolor)
getc.delete(0, END)
getc.insert(0, myColor[1])
choosecolor = "black"
def sure():
global choosecolor
choosecolor = getc.get()
showLab.config(bg=choosecolor)
def sure_fun(self):
sure()
tmpcolor: str
def erase():
global dercnt
global choosecolor
global tmpcolor
if dercnt == 0:
eraser.config(relief=RAISED)
tmpcolor = choosecolor
choosecolor = "#F0F0F0"
dercnt += 1
else:
eraser.config(relief=FLAT)
choosecolor = tmpcolor
dercnt -= 1
def paint(event):
YourChooseSize = sizevar.get()
x1, y1 = (event.x, event.y)
x2, y2 = (event.x+YourChooseSize, event.y+YourChooseSize)
canvas.create_oval(x1, y1, x2, y2, fill=choosecolor, outline=choosecolor)
def cls():
global choosecolor
getc.delete(0, END)
showLab.config(bg="white")
choosecolor = "black"
canvas.delete("all")
tk = Tk()
tk.title("Canvas Paint 1.1.3")
lab = Label(tk, text="拖拽鼠標繪圖,下面是更改畫筆顏色")
lab.pack()
# 詢問顏色部分
cco = Frame(tk, relief=SUNKEN)
cco.pack(pady=5)
# 需要一個展示框,一個文本框
tmplb1 = Label(cco, text="展示:")
showLab = Label(cco, width=15, relief=GROOVE, bg="white")
tmplb1.pack(side=LEFT)
showLab.pack(padx=10, side=LEFT)
tmplb2 = Label(cco, text="可輸入[#十六進制]和[顏色名] : string")
tmplb2.pack(side=LEFT)
getc = Entry(cco, width=30)
getc.pack(side=LEFT)
cokbtn = Button(cco, text="確認", command=sure)
getc.bind("<Return>", sure_fun)
cokbtn.pack(side=LEFT, ipadx=3, ipady=3)
askbtn = Button(cco, text="使用Ask", command=usingAsk)
askbtn.pack(side=RIGHT, ipadx=3, ipady=3)
# optionMenu
Omf = Frame(tk)
Omf.pack()
tmplb3 = Label(Omf, text="選擇畫筆寬度")
tmplb3.pack(side=LEFT)
sizevar = IntVar()
SizeList = [x for x in range(20, 90, 6)]
showoutput(SizeList)
sizevar.set(SizeList[0])
ShowOption = OptionMenu(Omf, sizevar, *SizeList)
ShowOption.pack(side=LEFT)
eraser = Button(Omf, text="橡皮", relief=FLAT, command=erase)
eraser.pack(side=LEFT, ipadx=20, padx=50)
canvas = Canvas(tk, width=640, height=300, relief=SUNKEN)
canvas.pack(expand=True, fill=BOTH)
btn = Button(tk, text="清除所有", command=cls)
btn.pack(pady=5)
canvas.bind("<B1-Motion>", paint)
canvas.mainloop()