Clock.schedule_once не обновляет метку, но вызывается метод update - PullRequest
0 голосов
/ 21 января 2019

У меня есть ярлык, в котором мне нужно обновить текст после получения текста с сервера.Метод работает, я получаю вывод, и функция также вызывается, но текст метки не обновляется.

Мой код:

#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Mon Jan 21 00:34:58 2019

@author: driftking9987
"""
from kivy.app import App
from kivy.uix.togglebutton import ToggleButton
from kivy.uix.widget import Widget
from kivy.uix.boxlayout import BoxLayout
import requests
from kivy.properties import StringProperty
from kivy.clock import Clock
import time

url = 'http://119.........'
l_server_text = "abc..."
l_server_text_waiting = "def..."
l_server_text_error = "ghi..."
self_global = ""

class HBoxWidget(BoxLayout):

    def __init__(self, **kwargs):
        super(HBoxWidget, self).__init__(**kwargs)

class VBoxWidget_Details(BoxLayout):
    label_name = StringProperty()

    def __init__(self, **kwargs):
        super(VBoxWidget_Details, self).__init__(**kwargs)
        self.label_name = l_server_text


    def updateText(self, *args):
        print("string to be updated is : ")
        print(l_server_text)
        print("updated")
        self.label_name = l_server_text


class ContainerBox(BoxLayout):
    def __init__(self, **kwargs):
        super(ContainerBox, self).__init__(**kwargs)

class WipApp(App):
    def build(self):
        global self_global
        self_global = self
        Clock.schedule_once(lambda dt: retrieveDataFromServer(self_global,12), 2)
        return ContainerBox() 


def retrieveDataFromServer(self,id):
    global l_server_text
    l_server_text = l_server_text_waiting
    print(l_server_text)
    a = VBoxWidget_Details()
    a.updateText(self)
    try:
        r_headers = {
        'Content-type': 'application/json',
        }
        data_post_req =  '{"id":'+str(id)+'}'
        print(data_post_req)
        response = requests.post('http://119....', headers=r_headers, data=data_post_req)
        res = response.json()
        output_text = res['Message']
        output_text = output_text.replace(':', '\n')
        print(output_text)
        l_server_text = output_text
        a = VBoxWidget_Details()
        a.updateText(self)
        print("done")
    except Exception as e:
        print("exception")
        l_server_text = l_server_text_error
        a = VBoxWidget_Details()
        a.updateText(self)


if __name__ == '__main__':
    wapp = WipApp()
    wapp.run()

Файл KV:

<HBoxWidget>:

    AnchorLayout:
        anchor_x: 'center'
        anchor_y: 'center'
        Image:
            source: '/Users/driftking9987/Desktop/fp.gif'
<VBoxWidget_Details>:
    BoxLayout:
        orientation: "horizontal"
        size: [1,.25]
        pos: root.pos
        Label:
            id: label_name
            text: root.label_name
            color: [0,84,80,19]
        Widget:

<ContainerBox>:
    orientation: 'vertical'
    Label:
        text: 'Label'
        size_hint_y: 0.1
    BoxLayout:
        id: four_horizontals
        orientation: 'horizontal'
        HBoxWidget:
        BoxLayout:
            orientation:'vertical'
            BoxLayout:
            BoxLayout:
                orientation:'vertical'
                VBoxWidget_Details:
            BoxLayout:

Ниже выводится вывод:

driftking9987$ python pp.py 
[INFO   ] [Logger      ] Record log in /Users/driftking9987/.kivy/logs/kivy_19-01-21_47.txt
[INFO   ] [Kivy        ] v1.10.1
[INFO   ] [Python      ] v3.6.8 |Anaconda custom (64-bit)| (default, Dec 29 2018, 19:04:46) 
[GCC 4.2.1 Compatible Clang 4.0.1 (tags/RELEASE_401/final)]
[INFO   ] [Factory     ] 194 symbols loaded
[INFO   ] [Image       ] Providers: img_tex, img_imageio, img_dds, img_sdl2, img_gif (img_pil, img_ffpyplayer ignored)
[INFO   ] [Text        ] Provider: sdl2
[INFO   ] [Window      ] Provider: sdl2
[INFO   ] [GL          ] Using the "OpenGL ES 2" graphics system
[INFO   ] [GL          ] Backend used <gl>
[INFO   ] [GL          ] OpenGL version <b'2.1 INTEL-12.4.7'>
[INFO   ] [GL          ] OpenGL vendor <b'Intel Inc.'>
[INFO   ] [GL          ] OpenGL renderer <b'Intel(R) Iris(TM) Graphics 650'>
[INFO   ] [GL          ] OpenGL parsed version: 2, 1
[INFO   ] [GL          ] Shading version <b'1.20'>
[INFO   ] [GL          ] Texture max size <16384>
[INFO   ] [GL          ] Texture max units <16>
[INFO   ] [Window      ] auto add sdl2 input provider
[INFO   ] [Window      ] virtual keyboard not allowed, single mode, not docked
[INFO   ] [GL          ] NPOT texture support is available
[INFO   ] [Base        ] Start application main loop
def...
string to be updated is : 
def...
updated
{"id":12}
KAM TRY
 logout
 Contac
string to be updated is : 
KAM TRY
 logout
 Contac
updated
done

А в приложении Kivy все, что я вижу, это abc текст метки.

Я планирую позвонить на retrieveDataFromServer рекурсивно после того, как какое-то условие выполнено, и это должно изменить текст, но это не происходит.

Есть идеи?

************************* ОБНОВЛЕНИЕ ****************************

Допустим, я просто хочу сослатьсяметка с идентификатором, тогда как мне это сделать?

<HBoxWidget>:

    AnchorLayout:
        anchor_x: 'center'
        anchor_y: 'center'
        Image:
            source: '/Users/driftking9987/Desktop/fp.gif'
<VBoxWidget_Details>:
    BoxLayout:
        orientation: "horizontal"
        size: [1,.25]
        pos: root.pos
        the_label_g_info: label_name
        Label:
            id: label_name
            text: root.label_name
            color: [0,84,80,19]
        Widget:

<ContainerBox>:
    orientation: 'vertical'
    title_name: title
    Label:
        id: title
        text: 'Label'
        size_hint_y: 0.1
    BoxLayout:
        box_name: box_id
        id: four_horizontals
        orientation: 'horizontal'
        HBoxWidget:
        BoxLayout:
            orientation:'vertical'
            BoxLayout:
            BoxLayout:
                id: box_id
                the_label_g_info: label_name
                orientation:'vertical'
                VBoxWidget_Details:
            BoxLayout:

Внутри метода updateText, если я пытаюсь написать self.the_label_g_info.text="drift", он говорит AttributeError: 'wapp' object has no attribute 'the_label_g_info'

Iзначит, как мне ссылаться на этикетку?Я пытаюсь от 2 дней, кажется, ничего не исправить.В то же время self.label_name = str(l_server_text) внутри __init__ из VBoxWidget_Details, кажется, правильно устанавливает текст во время инициализации.

1 Ответ

0 голосов
/ 21 января 2019

В вашем retrieveDataFromServer() методе я вижу:

    a = VBoxWidget_Details()
    a.updateText(self)

в двух местах.Этот код создает новый экземпляр VBoxWidget_Details и вызывает updateText() для этого нового экземпляра, а не для того, который вы отобразили.Вам, вероятно, нужно где-то сохранить ссылку на существующий VBoxWidget_Details и ссылаться на этот экземпляр в своем методе retrieveDataFromServer().

...