Kivy 简明教程
Kivy - Inputs
Kivy 框架具备接收和处理鼠标、触摸屏、陀螺仪、加速计等不同类型的输入的能力。Kivy 很多时候可以自动检测可用硬件。但是,如果你想支持自定义硬件,则需要对 kivy 适当进行配置。
由不同输入源产生的所有事件均由对应的事件类表示。MotionEvent 是针对指向设备(包括触摸和非触摸事件)提供的事件使用的基类。
-
Touch events — 一个至少包含一个 X 和 Y 位置的运动事件。所有触摸事件均在 Widget 树中分派。
-
No-touch events — 非触摸事件的一个示例是加速计,因为它是一个连续事件,没有位置。它没有开始或停止。这些事件不会在 Widget 树中分派。
Kivy 对输入应用后处理并对它进行分析以形成有意义的解释,例如:
-
是否是双击/三击检测?(根据距离和时间阈值)
-
当硬件不准确时让事件更加准确
-
如果原生触摸硬件发送的位置几乎相同,则减少事件的生成数量
经过处理后,运动事件会分派到 Window。如果它只是运动事件,它将分派到 on_motion()。另一方面,如果它是触摸事件,则触摸的 (x,y) 位置(0-1 范围)将按比例扩大到 Window 大小(宽度/高度),并分派到:
-
on_touch_down()
-
on_touch_move()
-
on_touch_up()
Example
在以下示例中,我们定义了一个名为 widget 的新类,它继承自 Widget。我们需要用以下语句导入 Widget 类:
from kivy.uix.widget import Widget
widget 类中有三个方法:
-
on_touch_down — 它是初始按压。
-
on_touch_move — 它是在按压后进行的移动。
-
on_touch_up - 这是媒体的“发布”。
class widget(Widget):
def on_touch_down(self, touch):
print("Down:",touch)
def on_touch_move(self, touch):
print("Move:",touch)
def on_touch_up(self, touch):
print("UP!",touch)
接下来,App 类的 build() 方法返回 widget() 对象。
class MotionApp(App):
def build(self):
return widget()
您可以通过点击和拖动屏幕来测试代码。您应该看到鼠标的所有移动和按压位置。
以下为 complete code ,可以保存并运行 -
from kivy.app import App
from kivy.uix.widget import Widget
from kivy.config import Config
# Configuration
Config.set('graphics', 'width', '720')
Config.set('graphics', 'height', '400')
Config.set('graphics', 'resizable', '1')
class widget(Widget):
def on_touch_down(self, touch):
print("Down:",touch)
def on_touch_move(self, touch):
print("Move:",touch)
def on_touch_up(self, touch):
print("UP!",touch)
class MotionApp(App):
def build(self):
return widget()
if __name__ == '__main__':
MotionApp().run()
Output
output 是一个不包含任何 UI 组件的空应用程序窗口。
在窗口中的任意位置单击鼠标。将捕获“on_touch_down”和“on_touch_up”事件,并显示鼠标触摸的位置,如下所示 -
Down: <MouseMotionEvent spos=(0.4228094575799722, 0.38596491228070173) pos=(304.0, 154.0)>
UP! <MouseMotionEvent spos=(0.4228094575799722, 0.38596491228070173) pos=(304.0, 154.0)>
Down: <MouseMotionEvent spos=(0.5730180806675939, 0.5137844611528822) pos=(412.0, 205.0)>
UP! <MouseMotionEvent spos=(0.5730180806675939, 0.5137844611528822) pos=(412.0, 205.0)>
Down: <MouseMotionEvent spos=(0.2517385257301808, 0.5588972431077694) pos=(181.0, 223.0)>
UP! <MouseMotionEvent spos=(0.2517385257301808, 0.5588972431077694) pos=(181.0, 223.0)>
MouseMotionEvent 的 spos 属性提供 0-1 坐标系中的相对位置。应用程序窗口的左下角对应于 (0,0),右上角对应于 (1,1)
pos 属性显示鼠标单击的实际坐标。在上述示例中,它在 (0,0) 位置向右 378.85 像素,向上 281.39 像素。
按住鼠标并将其移动到窗口中,您将获得 spos 和 pos 属性的瞬时变化值。例如 -
Move: <MouseMotionEvent spos=(0.41863699582753827, 0.5338345864661654) pos=(376.3546592489569, 266.38345864661653)>
Move: <MouseMotionEvent spos=(0.4172461752433936, 0.531328320802005) pos=(375.1043115438108, 265.1328320802005)>
Move: <MouseMotionEvent spos=(0.41585535465924894, 0.5288220551378446) pos=(373.8539638386648, 263.88220551378447)>
Event Profiles
基于输入提供程序和所用硬件的类型,事件配置文件包含有关输入事件的更多信息。该配置文件是 MotionEvent 对象的设备特定属性。例如,触摸输入具有 (x,y) 位置,但也可能具有压力信息、光斑大小、加速度向量等。
通过在 touch_down 事件处理程序中添加以下语句,我们可以找出当前设备支持的功能。
def on_touch_down(self, touch):
print(touch.profile)
output 将根据设备类型确定。它可以是 -
['pos', 'button']
或者,
['pos', 'angle']
Profile Values
以下是默认支持的一些配置文件值。
Sr.No |
Profile value & Description |
1 |
*Angle*2D 角度。通过“a”属性访问。 |
2 |
*Button*鼠标按钮('left'、'right'、'middle'、'scrollup' 或 'scrolldown')。通过按钮属性访问。 |
3 |
*Markerid*标记或定位标识符。通过 fid 属性访问。 |
4 |
*Pos*2D 位置。通过 x、y 或 pos 属性访问。 |
5 |
*pos3d*3D 位置。通过 x、y 或 z 属性访问。 |
6 |
*Pressure*接触压力。通过压力属性访问。 |
7 |
*形状*接触形状。可通过形状属性访问。 |
Touch Shape
在 Kivy 中,触摸事件期间的交互区域由“触摸形状”一词表示。它是指用于表示触摸或屏幕上触摸事件的几何形状。如果触摸具有形状,则会反映在“形状”属性中。
Kivy 支持的接触形状不同,有椭圆形、矩形、圆形和方形。
Double / Triple Tap
在多点触控设备中,双击是指在规定时间和距离内连续点击两次的操作。以类似的方式,设备可以识别“三击”操作。
事件对象具有“is_double_tap”属性和“is_triple_tap”属性,它们均会计算为 True 或 False。您可以测试当前触摸是否是双击:
def on_touch_down(self, touch):
if touch.is_double_tap:
print('Touch is a double tap!')
print(' - interval is', touch.double_tap_time)
print(' - distance between previous is', touch.double_tap_distance)
快速连续按鼠标按钮两次。您可获得类似于下面显示的结果:
Touch is a double tap!
- interval is 0.17462420463562012
- distance between previous is 0.0