1. 隨機(jī)顏色
通過(guò)前面的教程,咪博士已經(jīng)帶大家實(shí)現(xiàn)了畫板的繪圖功能。但是,現(xiàn)在畫板只能畫出黃色的圖案,還十分單調(diào),接下來(lái)咪博士就教大家,如何使用隨機(jī)顏色,讓畫板變得五彩斑斕。
改進(jìn)后的代碼如下:
from random import random
from kivy.app import App
from kivy.uix.widget import Widget
from kivy.graphics import Color, Ellipse, Line
class MyPaintWidget(Widget):
def on_touch_down(self, touch):
color = (random(), random(), random())
with self.canvas:
Color(*color)
d = 30.
Ellipse(pos=(touch.x - d / 2, touch.y - d / 2), size=(d, d))
touch.ud['line'] = Line(points=(touch.x, touch.y))
def on_touch_move(self, touch):
touch.ud['line'].points += [touch.x, touch.y]
class MyPaintApp(App):
def build(self):
return MyPaintWidget()
if __name__ == '__main__':
MyPaintApp().run()
試試看。怎么樣?是不是好看多了呢?
第 1 行 from random import random 我們導(dǎo)入了隨機(jī)函數(shù) random,它可以產(chǎn)生 [0, 1) 之間的隨機(jī)數(shù)
第 10 行 color = ( random () , random () , random () ) 通過(guò)調(diào)用 random 函數(shù),產(chǎn)生隨機(jī)的 RGB 分量,存儲(chǔ)在元組 color 中。后面(第 12 行),我們會(huì)用隨機(jī)的 RGB 分量合成隨機(jī)的顏色。注意,第 10 行的代碼位于 on_touch_down 函數(shù)內(nèi)。所以,用戶每次點(diǎn)擊鼠標(biāo)的時(shí)候,都會(huì)生成新的隨機(jī) RGB 分量。
第12 行,用前面(第 10 行)產(chǎn)生的隨機(jī) RGB 分量生成隨機(jī)顏色 color。函數(shù) Color 需要授受 3 個(gè)參數(shù)(分別表示 RGB 的 3 個(gè)分量)。這里的 Color (* color) 表示將元組 color 解包,傳遞給函數(shù) Color。由于元組 color 包含 3 個(gè)元素,所以它解包之后,就產(chǎn)生了 3 個(gè)隨機(jī)數(shù),而這 3 個(gè)隨機(jī)數(shù)恰好可以做為 RGB 的 3 個(gè)分量傳遞給函數(shù) Color。
不過(guò),由于現(xiàn)在的顏色是完全隨機(jī)的,程序有時(shí)候會(huì)產(chǎn)生一些比較暗的顏色,在黑色的畫板背景上顯示效果不是很好。我們可以進(jìn)一步限制隨機(jī)顏色的取值范圍,讓它只取一些比較鮮亮的顏色。
from random import random
from kivy.app import App
from kivy.uix.widget import Widget
from kivy.graphics import Color, Ellipse, Line
class MyPaintWidget(Widget):
def on_touch_down(self, touch):
color = (random(), 1, 1)
with self.canvas:
Color(*color, mode='hsv')
d = 30.
Ellipse(pos=(touch.x - d / 2, touch.y - d / 2), size=(d, d))
touch.ud['line'] = Line(points=(touch.x, touch.y))
def on_touch_move(self, touch):
touch.ud['line'].points += [touch.x, touch.y]
class MyPaintApp(App):
def build(self):
return MyPaintWidget()
if __name__ == '__main__':
MyPaintApp().run()
試試調(diào)整后的代碼。哇!頓時(shí)鮮艷多了。
第 10 行 color = ( random () , 1 , 1 ) 我們將隨機(jī)顏色的后 2 個(gè)分量固定為 1,只讓第 1 個(gè)分量隨機(jī)變化。
第 12 行 Color (* color , mode='hsv') 我們用 mode=’hsv’,指定顏色采用 HSV 模式,而不是先前默認(rèn)的 RGB 模式。HSV 色彩模式的 3 個(gè)參數(shù),分別代表 色調(diào)(Hue)、飽和度(Saturation)、明度(Value)。色調(diào)(Hue) 表示不同的色調(diào)(色彩的種類和名稱);飽和度(Saturation) 越高,則顏色越深、越艷;明度(Value)表示顏色的明度程度。由于采用了 HSV 色彩模式,第 10 行代碼產(chǎn)生的隨機(jī)元組 color 的含義也要相應(yīng)發(fā)生變化了。color 中的第 1 參數(shù)是一個(gè)隨機(jī)數(shù),表示隨機(jī)選擇不同的色彩種類;第 2 個(gè)參數(shù),固定為 1,表示取最大的飽和度,即將顏色調(diào)到最深、最艷;第 3 個(gè)參數(shù),也固定取 1,表示將顏色調(diào)到最亮。這樣改進(jìn)之后,程序就只會(huì)生成明亮的隨機(jī)顏色了。
2. 清除按鈕
最后,我們要在畫板上添加一個(gè)清除按鈕,這樣用戶不必重啟程序,就能將畫板清空,并繪制新的圖形。
完整代碼如下:
from random import random
from kivy.app import App
from kivy.uix.widget import Widget
from kivy.uix.button import Button
from kivy.graphics import Color, Ellipse, Line
class MyPaintWidget(Widget):
def on_touch_down(self, touch):
color = (random(), 1, 1)
with self.canvas:
Color(*color, mode='hsv')
d = 30.
Ellipse(pos=(touch.x - d / 2, touch.y - d / 2), size=(d, d))
touch.ud['line'] = Line(points=(touch.x, touch.y))
def on_touch_move(self, touch):
touch.ud['line'].points += [touch.x, touch.y]
class MyPaintApp(App):
def build(self):
parent = Widget()
self.painter = MyPaintWidget()
clearbtn = Button(text='Clear')
clearbtn.bind(on_release=self.clear_canvas)
parent.add_widget(self.painter)
parent.add_widget(clearbtn)
return parent
def clear_canvas(self, obj):
self.painter.canvas.clear()
if __name__ == '__main__':
MyPaintApp().run()
點(diǎn)擊左下角的清除(Clear)按鈕,可以將畫板的內(nèi)容清空。
第 5 行 from kivy.uix.button import Button 導(dǎo)入 Button 類。窗體左下角的清除 (Clear) 按鈕,便是 Button 類的實(shí)例。
第 24 行 parent = Widget () 創(chuàng)建一個(gè)空的窗口部件 (Widget)。后面我們會(huì)將自定義窗口部件(畫板 MyPaintWidget)以及清除按鈕(Button)添加到 parent 上。注意:Kivy 中進(jìn)行窗口部件編排的標(biāo)準(zhǔn)做法是使用布局( layout)。咪博士這里用的是比較便捷(但不規(guī)范)的方法,為的是讓大家快速完成簡(jiǎn)易畫板這個(gè)項(xiàng)目。關(guān)于 Kivy 中布局(layout)的使用,咪博士將在其他的教程中專門講解。
第25 行 self.painter = MyPaintWidget() 創(chuàng)建自定義窗口部件對(duì)象,并賦值給變量 self.painter。因?yàn)椋竺嫖覀冞€要在別的函數(shù)中引用它。
第 26 行 clearbtn = Button (text='Clear') 創(chuàng)建清除按鈕對(duì)象,將按鈕的文字設(shè)置為 Clear,并賦值給變量 clearbtn。
第 27 行 clearbtn.bind (on_release=self.clear_canvas) 將清除按鈕的 on_release 事件綁定 (bind) 到 self.clear_canvas 方法(第 32, 33 行)。這樣,當(dāng)用戶按下并釋放清除按鈕時(shí),將觸發(fā)按鈕的 on_release 事件,然后調(diào)用該事件所綁定的 self.clear_canvas 方法,執(zhí)行清除畫板的動(dòng)作。
第 28, 29 行,將自定義窗口部件對(duì)象(self.painter)和清除按鈕對(duì)象(clearbtn)添加到 parent 窗口部件中。
第 30 行 return parent 返回 parent 窗口部件。注意,此時(shí)的 parent 已經(jīng)包含了自定義窗口部件對(duì)象(self.painter)和清除按鈕對(duì)象(clearbtn)。
第 32, 33 行,是用戶按下并釋放清除按鈕時(shí)觸發(fā)的回調(diào)函數(shù)。清除畫板的功能正是通過(guò)第 33 行 self.painter.canvas.clear() 實(shí)現(xiàn)的。
好啦,到此為止 Kivy 簡(jiǎn)易畫板的項(xiàng)目就全部完成啦。請(qǐng)關(guān)注咪博士后續(xù)更加精彩的 Kivy 教程。
原文鏈接:http://www.ipaomi.com/2017/11/20/kivy-中文教程-實(shí)例入門-簡(jiǎn)易畫板-simple-paint-app:3-隨機(jī)顏色及清/