Kivy: Текст моего ярлыка не обновляется после добавления экранов - PullRequest
0 голосов
/ 05 апреля 2019

Итак, я хотел прочитать данные с моего Arduino до serial port и обновить данные, которые я прочитал, до текста метки для отображения.Он работает, когда у меня есть только простой код для простого чтения и обновления, но когда я добавляю ScreenManager и Screen, он перестает обновлять текст.

В конце концов мне понадобится другая анимация в соответствии ск полученным данным, это больше о тестировании, если эта функция работает

Заранее спасибо!

Вот весь мой код

import os
os.environ['KIVY_GL_BACKEND'] ='gl'

from kivy.app import App
from kivy.lang import Builder
from kivy.uix.widget import Widget
from kivy.properties import (NumericProperty, StringProperty, ReferenceListProperty, ObjectProperty, ListProperty)
from kivy.clock import Clock
from kivy.vector import Vector
from kivy.core.text import LabelBase
from kivy.uix.screenmanager import ScreenManager, Screen, FadeTransition


LabelBase.register(name='Sans',fn_regular="Sansation-Regular.ttf")

import serial

kivy = Builder.load_string("""
#:import FadeTransition kivy.uix.screenmanager.FadeTransition
<MyManager>:
    transition: FadeTransition()
    MainScreen:
    OperationScreen:

<MainScreen>:
    name: 'main'
    Label:
        text: 'Welcome'
        font_size: 40
        on_touch_up : app.root.current = 'operation'

    Label:
        text: 'dafault'
        font_size: 20
        pos: -200,-100
        id: data_label


<OperationScreen>:
    name: 'operation'
    Label:
        text: 'Youre in'
        font_size: 40
""")   

class OperationScreen(Screen):
    pass

class MainScreen(Screen):
    def __init__(self,**kwargs):
        super(MainScreen,self).__init__(**kwargs)

    def Read(self,dt):
        Clock.unschedule(self.Read)
        data = arduino.readline()
        if data != '':
            self.ids.data_label.text = data
        Clock.schedule_once(self.Read)
    pass

class MyManager(ScreenManager):
    pass

class mainApp(App):
    Main = MainScreen()
    def build(self):
        Clock.schedule_once(self.Main.Read)
        return MyManager()

if __name__ == '__main__':
    try:
        arduino = serial.Serial('/dev/ttyACM0', 9600, timeout=1)
    except:
        print("failed to connect")
    mainApp().run()

Я ожидаю, что этикетка стекст 'default' будет меняться соответственно, но он просто замерз с 'default'

1 Ответ

1 голос
/ 05 апреля 2019

Проблема

Когда ваше приложение работает, есть два экземпляра class MainScreen.Один был создан в файле kv.Другой экземпляр был создан вручную, Main = MainScreen() в class mainApp.

Планирование метода Read() в экземпляре, созданном вручную, Main = MainScreen(), и с ним не связано модальное представление.

Решение

  • В файле kv добавить id: main_screen для MainScreen:
  • Удалить Main = MainScreen() в class mainApp
  • Реализовать конструктордля class MyManager()
  • Переместите планирование из class mainApp в конструктор class MyManager()
  • . В вашем случае лучше использовать Clock.create_trigger() вместо Clock.schedule_once()
  • Правильный способ отменить событие Clock: event.cancel() или Clock.unschedule(event)

Пример

main.py

import os

os.environ['KIVY_GL_BACKEND'] = 'gl'

from kivy.app import App
from kivy.lang import Builder
from kivy.uix.widget import Widget
from kivy.properties import (NumericProperty, StringProperty, ReferenceListProperty, ObjectProperty, ListProperty)
from kivy.clock import Clock
from kivy.vector import Vector
from kivy.core.text import LabelBase
from kivy.uix.screenmanager import ScreenManager, Screen, FadeTransition

# LabelBase.register(name='Sans', fn_regular="Sansation-Regular.ttf")

import serial

kivy = Builder.load_string("""
#:import FadeTransition kivy.uix.screenmanager.FadeTransition
<MyManager>:
    transition: FadeTransition()
    MainScreen:
        id: main_screen
    OperationScreen:

<MainScreen>:
    name: 'main'
    Label:
        text: 'Welcome'
        font_size: 40
        on_touch_up : app.root.current = 'operation'

    Label:
        text: 'dafault'
        font_size: 20
        pos: -200,-100
        id: data_label


<OperationScreen>:
    name: 'operation'
    Label:
        text: 'Youre in'
        font_size: 40
""")


class OperationScreen(Screen):
    pass


class MainScreen(Screen):

    def Read(self, dt):
        data = str(dt)
        # data = arduino.readline()
        if data != '':
            self.ids.data_label.text = data
            self.manager.event_trigger()
        else:
            self.manager.event_trigger.cancel()


class MyManager(ScreenManager):
    event_trigger = ObjectProperty(None)

    def __init__(self, **kwargs):
        super(MyManager, self).__init__(**kwargs)
        self.event_trigger = Clock.create_trigger(self.ids.main_screen.Read)
        self.event_trigger()


class mainApp(App):

    def build(self):
        return MyManager()


if __name__ == '__main__':
    # try:
    #     arduino = serial.Serial('/dev/ttyACM0', 9600, timeout=1)
    # except:
    #     print("failed to connect")
    mainApp().run()

Выход

Result

...