ae.kivy_sideloading

kivy mixin and widgets to integrate a sideloading server in your app

this namespace portion provides widgets and a mixin class for your main app instance to easily integrate and control the ae sideloading server into your main app.

kivy sideloading integration into your main app class

add the SideloadingMainAppMixin mixin provided by this ae namespace portion to your main app class:

class MyMainAppClass(SideloadingMainAppMixin, KivyMainApp):

the sub-app of the sideloading server will then automatically be instantiated when your app starts and will initialize the sideloading_app attribute with this sub-app instance.

Hint

if you prefer to instantiate the sideloading server sub-app manually, then specify SideloadingMainAppMixin after KivyMainApp in the declaration of your main app class.

adding sideloading_active to the :ref:`app state variables of your app’s config files will ensure that the running status of the sideloading server gets automatically stored persistent on pause or stop of the app for the next app start.

the running status of the sideloading server will be restored in the app start event handler method (on_app_run()).

to manually start it offering the APK of the embedding app, call the on_sideloading_server_start() method passing an empty string and dict:

self.on_sideloading_server_start("", {})

Hint

when you pass the dict with a number in a ‘port’ key, then it will be used as the server listening port.

if no ‘port’ gets specified, then SideloadingMainAppMixin will calculate an individual port number from the first character of the app_name of the app mixing in this class. this is to prevent the server socket error [Errno 98] Address already in use if two different applications with sideloading are running on the same device and want to offer sideloading.

to manually pause the sideloading server, call the on_sideloading_server_stop() method passing an empty string and dict:

self.on_sideloading_server_stop("", {})

usage of the sideloading button

this ae namespace portion is additionally providing the SideloadingButton flow button widget to integrate it in your Kivy app. This button can be used to:

  • start or stop the sideloading server,

  • select a file for sideloading via the FileChooserPopup.

  • display file info like the full file path and file length.

  • display the URL of your sideloading server as QR code to allow connections from other devices.

to optionally integrate this SideloadingButton into your app, add it to the root layout in your app’s main kv file with the id sideloading_button:

MyRootLayout:
    ...
    SideloadingButton:
        id: sideloading_button

if the sideloading server is not active and the user is clicking the SideloadingButton, then this portion will first check if the Downloads folder of the device is containing an APK file for the running app, and if yes, then the sideloading server will be started providing the found APK file.

ff the sideloading server is instead already running/active, and the user is tapping on the SideloadingButton then a dropdown menu will be shown with options to (1) display info of the sideloading file, (2) select a new file, (3) display the sideloading server URL as QR code or (4) stop the sideloading server.

dependencies/requirements in buildozer.spec

to build an Android APK with the kivy sideloading server integrated, make sure that the following external packages are specified in the requirements setting of the [app] section of your buildozer.spec file.

  • ae.kivy_file_chooser

  • ae.kivy_iterable_displayer

  • ae.kivy_qr_displayer

  • ae.kivy_sideloading

  • ae.sideloading_server

  • kivy_garden.qrcode

  • qrcode

  • typing_extensions

additionally, the following packages and ae namespace portions required by the above packages have to be included:

typing_extensions, qrcode, kivy_garden.qrcode,
ae.base, ae.files, ae.paths, ae.deep, ae.dynamicod, ae.i18n,
ae.updater, ae.core, ae.literal, ae.console, ae.parse_date, ae.gui,
ae.kivy_auto_width, ae.kivy_dyn_chi, ae.kivy_relief_canvas, ae.kivy, ae.kivy_user_prefs, ae.kivy_glsl,
ae.kivy_file_chooser, ae.sideloading_server, ae.kivy_sideloading,
ae.kivy_iterable_displayer, ae.kivy_qr_displayer

sideloading server life cycle

to activate the sideloading server to offer a different file, specify the path (or glob file mask) of the file to be offered/available via sideloading in the sideloading_file_mask attribute and then call the method on_sideloading_server_start(). this method will check if the specified file

exists, and if yes, then it will start the sideloading server. if you specify a file mask instead of a concrete

file path, then this method will check if there exists exactly one file matching the file mask.

after the start of the sideloading server, the sideloading_file_ext attribute will contain the file extension of the file available via sideloading.

the sideloading server will automatically be shut down on quit/close of the embedding app. you can alternatively stop the sideloading server manually at any time by calling the on_sideloading_server_stop() method.

Classes

SideloadingMainAppMixin()

mixin class with default methods for the main app class.

SideloadingMenuPopup(**kwargs)

dropdown menu to control sideloading server.

SideloadingMenuTour(main_app)

user preferences menu tour.

class SideloadingMenuPopup(**kwargs)[source]

Bases: FlowDropDown

dropdown menu to control sideloading server.

__init__(**kwargs)[source]
class SideloadingMenuTour(main_app)[source]

Bases: TourDropdownFromButton

user preferences menu tour.

__init__(main_app)[source]
class SideloadingMainAppMixin[source]

Bases: object

mixin class with default methods for the main app class.

app_name: str
change_app_state: Callable
change_flow: Callable
dpo: Callable
framework_root: Widget
get_option: Callable
show_message: Callable
user_specific_cfg_vars: set
vpo: Callable
file_chooser_initial_path: str = ''

used by file_chooser to select a sideloaded file

file_chooser_paths: list[str] = []

recently used paths as app state for file chooser

sideloading_active: tuple = ()

app state flag if the sideloading server is running

sideloading_app: SideloadingServerApp

http sideloading server console app

sideloading_file_ext: str = '.'

extension of the selected sideloading file

sideloading_file_mask: str = ''

file mask of the sideloading file

_init_default_user_cfg_vars()[source]
on_app_run()[source]

run app event.

on_app_state_version_upgrade(from_version)[source]

upgrade app state config vars from the specified app state version to the next one.

Parameters:

from_version (int) – app state version to upgrade from.

on_app_started()[source]

initialize and start shaders after kivy app, window and widget root got initialized.

on_debug_level_change(level_name, _event_kwargs)[source]

debug level app state change flow change confirmation event handler.

Parameters:
  • level_name (str) – the new debug level name to be set (passed as flow key).

  • _event_kwargs (dict[str, Any]) – unused event kwargs.

Return type:

bool

Returns:

True to confirm the debug level change.

on_file_chooser_submit(file_path, chooser_popup)[source]

event callback from FileChooserPopup.on_submit() on selection of a file.

Parameters:
  • file_path (str) – path string of the selected file.

  • chooser_popup (Widget) – file chooser popup/container widget.

on_sideloading_server_start(_flow_key, event_kwargs)[source]

start the sideloading server.

Parameters:
  • _flow_key (str) – unused/empty flow key.

  • event_kwargs (dict[str, Any]) – event kwargs: * ‘port’: TCP/IP server listening port. * ‘tap_widget’: button instance that initiated the start of the server.

Return type:

bool

Returns:

always True to confirm change of flow id.

on_sideloading_server_stop(_flow_key, _event_kwargs)[source]

stop a running sideloading http server.

Parameters:
  • _flow_key (str) – unused/empty flow key.

  • _event_kwargs (dict[str, Any]) – unused event kwargs.

Return type:

bool

Returns:

always True to confirm change of flow id.