Table des matières
Kivy: Comment faire ou ne pas faire un tas de chose
Comment chercher ?
Sur internet
- Dans la doc officielle, mais les chances de trouver sont quasi nulles.
- Dans un moteur de recherche: ça finit souvent par des posts sur stackoverflow, avec des réponses
médiocresfausses. - geeksforgeeks.org est récent et plutôt bien.
Une bonne solution: Les exemples des sources de kivy
Gallery of Examples
Gallery of Examples Il faut fouiller!
Des explications avec les exemples des sources
Une liste de scripts qui explique bien:
- pos_hint : boxlayout_poshint.py
- bubble : bubble_test.py
- camera : camera.py
- carousel : carousel_buttons.py
- mipmap : label_mipmap.py
- text_size = textwrap : label_text_size.py
- text with markup : label_with_markup.py
- popup : popup_with_kv.py
- scatter : scatter.py et scatter.kv
- scrollview : scrollview.py et scrollview.kv
- splitter : splitter.py
- tabbed panel = onglet : tabbedpanel.py
- text align : textalign.py textalign.kv
- video player : videoplayer.py
- ErrorPopup(Popup) : main.py et text2speechdemo.kv
- Slider : circle.py
- Clock : Pong ou mesh_manipulation.py
Adapter la résolution dpi sur son PC
- Sur votre PC, définir la taille de votre fenêtre
from plyer import utils from oscpy.client import OSCClient from oscpy.server import OSCThreadServer print("Platform =", utils.platform) ANDROID = utils.platform._platform_android # retourne True ou False print("Android =", ANDROID) if not ANDROID: from kivy.core.window import Window # Simulation de l'écran de mon tél: 1280*720 k = 0.8 WS = (int(720*k), int(1280*k)) Window.size = WS os.environ['JAVA_HOME'] = '/usr/lib/jvm/adoptopenjdk-8-hotspot-amd64' from jnius import autoclass
Lancer le main.py avec:
KIVY_METRICS_FONTSCALE=1.2 python3 main.py
avec une valeur “1.2” à adapter pour que vous ayez le même graphisme sur votre PC que sur votre téléphone.
Comment lister tous les widgets dans le python
Par exemple, extrait de smartcitizen main.py#L83:
# Recherche de tous les widgets de self print([type(widget) for widget in self.walk(loopback=True)]) # Recherche de tous les widgets de Screen1 print(self.ids.sm) f = self.ids.sm.get_screen("first") print([type(widget) for widget in f.walk(loopback=True)])
Sortie de [type(widget) for widget in self.walk(loopback=True)] dans SmartCitizen()
<class '__main__.SmartCitizen'>, <class 'kivy.uix.actionbar.ActionBar'>, <class 'kivy.uix.actionbar.ActionView'>, <class 'kivy.uix.actionbar.ActionButton'>, <class 'kivy.uix.image.Image'>, <class 'kivy.uix.screenmanager.ScreenManager'>, <class '__main__.MainScreen'>, <class 'kivy.uix.boxlayout.BoxLayout'>, <class 'kivy.uix.label.Label'>, <class 'kivy.uix.boxlayout.BoxLayout'>, ......
Comment passer un attribut d'une class à une autre
En fait, comment passer d'un objet à un autre !
Faire des print(de quoi ?). Commencer par
print(dir(self))
puis dans la liste des méthodes et attributs, ayez de nez. Si app est dans la liste:
print(dir(self.app))
Comment récupérer self.app dans tous les objets
Une solution élégante est utilisée dans accelerometer: main.py avec ces extraits modifiés pour expliquer:
class AccelerometerApp(App): def build(self): return Accelerometer(self) class Accelerometer(BoxLayout): def __init__(self, app, **kwargs): super().__init__(**kwargs) self.app = app self.app.osc = OSC() class OSC: def __init__(self): self.histo = [] self.server = OSCThreadServer() self.server.bind(b'/histo', self.on_histo) def on_histo(self, *args): self.histo = .... class Screen2: def __init__(self): self.app = App.get_running_app() # et appel de l'attribut histo de OSC avec self.app.osc.histo Clock.schedule_once(self._once, 1) def _once(self, dt): Clock.schedule_interval(self.update, 0.1) def update(self, dt): blabla = self.app.osc.histo # blabla retrouve la valeur de histo de OSC !!!!
Pourquoi définir les attributs appelés dans *.kv comme attributs de classe ?
Parce que c'est comme ça ? Quand lama fâché, lui toujours faire ainsi !
Voir l'exemple ci-dessous.
Comment changer la couleur d'un Rectangle ?
Répond aussi à la Question:
Comment définir et accéder aux attributs dans le main et le *.kv ?
Les attributs des widgets défini dans le *.kv sont accessibles depuis le main, seulement si les attributs du widget sont définis en attribut de classe.
Exemple extrait de multipong:
*.kv
<PongPaddle>: canvas: Color: rgb: self.rect_color Rectangle: pos: self.pos size: root.height/65, root.height/7 <Screen1>: ... ... paddle_0: paddle0 ... ... PongPaddle: # paddle_0 id: paddle0 pos: self.pos ... ... BoxLayout: orientation: 'horizontal' BoxLayout: size_hint_x: 0.70 canvas: Color: rgba: 1, 1, 1, 1 Line: points: [int(x*(root.top/720)) for x in root.points] joint: 'miter' width: 3 close: 1
extrait de main.py
... ... class PongPaddle(Widget): rect_color = ListProperty([1, 1, 1]) angle = NumericProperty(0) ... ... class Screen1(Screen): ... ... def apply_paddle_red_color(self, my_num): if my_num == 0: self.paddle_0.rect_color = 1, 0, 0 ... ...
Button background_color
Button: background_normal: '' background_color: 1, .3, .4, .85
Pour avoir des couleurs flashy, mettre des valeurs supérieures à 1: exemple
background_color: (0, 1.2, 0, 1)
Texte en gras dans un label
Label: canvas.before: Color: rgba: 1, 1, 1, 1 Rectangle: pos: self.pos size: self.size size_hint_y: 0.10 markup: True text: '[b]' + "Mon texte" + '[/b]' color: 1, 0, 0.5, 1
Factory
Factory peut être utilisée pour enregistrer automatiquement toute classe ou module et en instancier des classes n'importe où dans votre projet.
- API Factory using-factory-objects-in-kivy I'm not sure of everything the Factory is used for … Les exemples de la doc qui l'utilisent sont irréels ….
Réception sur Android en Multicast
Dans buildozer.spec, définir:
android.permissions = INTERNET,CHANGE_WIFI_MULTICAST_STATE,ACCESS_NETWORK_STATE,ACCESS_WIFI_STATE
Les permissions définies dans buildozer.spec crée le bouton enable/disable dans Android / Paramètres / Application pour certaine permission: par défaut, il est disable. Quand ça ne marche pas, c'est la première chose à regarder.
Twisted dans kivy
- Integrating with other Frameworks propose l'intégration des 2 !
- Exemple avec Apprendre Kivy
Comment éviter ou résoudre des bugs à la compilation avec buildozer
Comment commenter dans buildozer.spec ?
Ne pas faire:
requirements = python3,kivy,plyer,numpy,oscpy#,jnius ni requirements = python3,kivy,plyer,numpy,oscpy #,jnius
mais
requirements = python3,kivy,plyer,numpy,oscpy #,jnius
Le buildozer.spec est seulement presque du python. Ce commentaire maltapropo m'a donné des messages d'erreurs avec buildozer parlant de No module named 'encodings'
Bugs
Novembre 2020
Voir xclip and xsel
[CRITICAL] [Cutbuffer ] Unable to find any valuable Cutbuffer provider. xclip - FileNotFoundError: [Errno 2] Aucun fichier ou dossier de ce type: 'xclip'
résolu avec
sudo apt install xclip
Comment avoir une action maintenue si maintien d'un Button
- accelerometer.kv
Button: id: recul markup: True background_color: (0, 1.2, 0, 1) font_size: "18sp" text: '[b]<<<[/b]' on_press: root.do_back_forward(-1) on_release: root.do_end() Button: id: avance markup: True background_color: (0, 1.2, 0, 1) font_size: "18sp" text: '[b]>>>[/b]' on_press: root.do_back_forward(1) on_release: root.do_end()
- main.py
def do_back_forward(self, sens): self.bf = 1 bt = Thread(target=self.back_forward_loop, args=(sens, ), daemon=True) bt.start() def back_forward_loop(self, sens): while self.bf: sleep(0.1) self.gap = self.gap + sens*10 if self.gap > 0: self.gap = 0 l = len(self.app.osc.histo_xyz) if self.gap < -l + 500: self.gap = -l + 500 print("Gap:", self.gap) def do_end(self): self.bf = 0