Version

Quick search

Motion Event

The MotionEvent is the base class used for events provided by pointing devices (touch and non-touch). This class defines all the properties and methods needed to handle 2D and 3D movements but has many more capabilities.

Usually you would never need to create the MotionEvent yourself as this is the role of the providers.

Flow of the motion events

  1. The MotionEvent ‘s are gathered from input providers by EventLoopBase.

  2. Post processing is performed by registered processors postproc.

  3. EventLoopBase dispatches all motion events using on_motion event to all registered listeners including the WindowBase.

  4. Once received in on_motion() events (touch or non-touch) are all registered managers. If a touch event is not handled by at least one manager, then it is dispatched through on_touch_down(), on_touch_move() and on_touch_up().

  5. Widgets receive events in on_motion() method (if passed by a manager) or on on_touch_xxx methods.

Motion events and event managers

A motion event is a touch event if its MotionEvent.is_touch is set to True. Beside is_touch attribute, MotionEvent.type_id can be used to check for event’s general type. Currently two types are dispatched by input providers: “touch” and “hover”.

Event managers can be used to dispatch any motion event throughout the widget tree and a manager uses type_id to specify which event types it want to receive. See eventmanager to learn how to define and register an event manager.

A manager can also assign a new type_id to MotionEvent.type_id before dispatching it to the widgets. This useful when dispatching a specific event:

class MouseTouchManager(EventManagerBase):

    type_ids = ('touch',)

    def dispatch(self, etype, me):
        accepted = False
        if me.device == 'mouse':
            me.push() # Save current type_id and other values
            me.type_id = 'mouse_touch'
            self.window.transform_motion_event_2d(me)
            # Dispatch mouse touch event to widgets which registered
            # to receive 'mouse_touch'
            for widget in self.window.children[:]:
                if widget.dispatch('on_motion', etype, me):
                    accepted = True
                    break
            me.pop() # Restore
        return accepted

Listening to a motion event

If you want to receive all motion events, touch or not, you can bind the MotionEvent from the Window to your own callback:

def on_motion(self, etype, me):
    # will receive all motion events.
    pass

Window.bind(on_motion=on_motion)

You can also listen to changes of the mouse position by watching mouse_pos.

Profiles

The MotionEvent stores device specific information in various properties listed in the profile. For example, you can receive a MotionEvent that has an angle, a fiducial ID, or even a shape. You can check the profile attribute to see what is currently supported by the MotionEvent provider.

This is a short list of the profile values supported by default. Please check the MotionEvent.profile property to see what profile values are available.

Profile value

Description

angle

2D angle. Accessed via the a property.

button

Mouse button (‘left’, ‘right’, ‘middle’, ‘scrollup’ or ‘scrolldown’). Accessed via the button property.

markerid

Marker or Fiducial ID. Accessed via the fid property.

pos

2D position. Accessed via the x, y or pos properties.

pos3d

3D position. Accessed via the x, y or z properties.

pressure

Pressure of the contact. Accessed via the pressure property.

shape

Contact shape. Accessed via the shape property .

If you want to know whether the current MotionEvent has an angle:

def on_touch_move(self, touch):
    if 'angle' in touch.profile:
        print('The touch angle is', touch.a)

If you want to select only the fiducials:

def on_touch_move(self, touch):
    if 'markerid' not in touch.profile:
        return
class kivy.input.motionevent.MotionEvent(device, id, args, is_touch=False, type_id=None)[source]

Bases: kivy.input.motionevent.MotionEvent

Abstract class that represents an input event.

Parameters:
id: str

unique ID of the MotionEvent

args: list

list of parameters, passed to the depack() function

apply_transform_2d(transform)[source]

Apply a transformation on x, y, z, px, py, pz, ox, oy, oz, dx, dy, dz.

button

Currently pressed button.

copy_to(to)[source]

Copy some attribute to another motion event object.

depack(args)[source]

Depack args into attributes of the class

device

Device used for creating this event.

dispatch_done()[source]

Notify that dispatch to the listeners is done.

Called by the EventLoopBase.post_dispatch_input().

New in version 2.1.0.

dispatch_mode

(Experimental) Used by a event manager or a widget to assign the dispatching mode. Defaults to MODE_DEFAULT_DISPATCH. See eventmanager for available modes.

New in version 2.1.0.

distance(other_touch)[source]

Return the distance between the two events.

double_tap_time

If the touch is a is_double_tap, this is the time between the previous tap and the current touch.

property dpos

Return delta between last position and current position, in the screen coordinate system (self.dx, self.dy).

dsx

Delta between self.sx and self.psx, in 0-1 range.

dsy

Delta between self.sy and self.psy, in 0-1 range.

dsz

Delta between self.sz and self.psz, in 0-1 range.

dx

Delta between self.x and self.px, in window range.

dy

Delta between self.y and self.py, in window range.

dz

Delta between self.z and self.pz, in window range.

grab(class_instance, exclusive=False)[source]

Grab this motion event.

If this event is a touch you can grab it if you want to receive subsequent on_touch_move() and on_touch_up() events, even if the touch is not dispatched by the parent:

def on_touch_down(self, touch):
    touch.grab(self)

def on_touch_move(self, touch):
    if touch.grab_current is self:
        # I received my grabbed touch
    else:
        # it's a normal touch

def on_touch_up(self, touch):
    if touch.grab_current is self:
        # I receive my grabbed touch, I must ungrab it!
        touch.ungrab(self)
    else:
        # it's a normal touch
        pass

Changed in version 2.1.0: Allowed grab for non-touch events.

grab_current

Used to determine which widget the event is being dispatched to. Check the grab() function for more information.

id

Id of the event, not unique. This is generally the Id set by the input provider, like ID in TUIO. If you have multiple TUIO sources, then same id can be used. Prefer to use uid attribute instead.

is_double_tap

Indicate if the touch event is a double tap or not.

property is_mouse_scrolling

Returns True if the touch event is a mousewheel scrolling

New in version 1.6.0.

is_touch

True if the MotionEvent is a touch.

is_triple_tap

Indicate if the touch event is a triple tap or not.

New in version 1.7.0.

move(args)[source]

Move to another position.

property opos

Return the initial position of the motion event in the screen coordinate system (self.ox, self.oy).

osx

Origin X position, in 0-1 range.

osy

Origin Y position, in 0-1 range.

osz

Origin Z position, in 0-1 range.

ox

Origin X position, in window range.

oy

Origin Y position, in window range.

oz

Origin Z position, in window range.

pop()[source]

Pop attributes values from the stack.

pos

Position (X, Y), in window range.

property ppos

Return the previous position of the motion event in the screen coordinate system (self.px, self.py).

profile

Profiles currently used in the event.

psx

Previous X position, in 0-1 range.

psy

Previous Y position, in 0-1 range.

psz

Previous Z position, in 0-1 range.

push(attrs=None)[source]

Push attribute values in attrs onto the stack.

push_attrs_stack

Attributes to push by default, when we use push() : x, y, z, dx, dy, dz, ox, oy, oz, px, py, pz.

px

Previous X position, in window range.

py

Previous Y position, in window range.

pz

Previous Z position, in window range.

scale_for_screen(w, h, p=None, rotation=0, smode='None', kheight=0)[source]

Scale position for the screen.

Changed in version 2.1.0: Max value for x, y and z is changed respectively to w - 1, h - 1 and p - 1.

shape

Shape of the touch event, subclass of Shape. By default, the property is set to None.

property spos

Return the position in the 0-1 coordinate system (self.sx, self.sy).

sx

X position, in 0-1 range.

sy

Y position, in 0-1 range.

sync_with_dispatch

If set to True (default) keeps first previous position (X, Y, Z in 0-1 range) and ignore all other until MotionEvent.dispatch_done() is called from the EventLoop.

This attribute is needed because event provider can make many calls to MotionEvent.move(), but for all those calls event is dispatched to the listeners only once. Assigning False will keep latest previous position. See MotionEvent.move().

New in version 2.1.0.

sz

Z position, in 0-1 range.

time_end

Time of the end event (last event usage).

time_start

Initial time of the event creation.

time_update

Time of the last update.

to_absolute_pos(nx, ny, x_max, y_max, rotation)[source]

Transforms normalized (0-1) coordinates nx and ny to absolute coordinates using x_max, y_max and rotation.

Raises:

ValueError: If rotation is not one of: 0, 90, 180 or 270

New in version 2.1.0.

triple_tap_time

If the touch is a is_triple_tap, this is the time between the first tap and the current touch.

New in version 1.7.0.

type_id

(Experimental) String to identify event type.

New in version 2.1.0.

ud

User data dictionary. Use this dictionary to save your own data on the event.

uid

Uniq ID of the event. You can safely use this property, it will be never the same across all existing events.

ungrab(class_instance)[source]

Ungrab a previously grabbed motion event.

x

X position, in window range.

y

Y position, in window range.

z

Z position, in window range.