从另一个类 - Python和Kivy访问方法中的变量

时间:2017-10-06 08:23:57

标签: python kivy kivy-language

我正在与kivy合作开发一个应用程序,它将在几个屏幕上打印数字。

现在是从一个屏幕打印值,但我还必须在其他两个屏幕上显示值,问题是我正在调用一个类中的方法以及时连续运行并更新变量值,我希望从其他类中的方法查询或访问这些变量以在其他屏幕中打印它们,每个类代表一个屏幕,因此它们必须存在于代码中。

我想知道这是否可行,我怎样才能实现解决方案呢。

让我分享一下我的代码,它非常大,所以我只会粘贴相关的代码:

gui.py

from kivy.app import App
from kivy.lang import Builder
from kivy.uix.screenmanager import ScreenManager, Screen, FadeTransition
from kivy.properties import ObjectProperty, StringProperty, NumericProperty
from kivy.uix.gridlayout import GridLayout
from kivy.clock import Clock

# Creating dynamic variables
class Show_Val(Screen):
    timer_update = NumericProperty(0)
    dist_travel = NumericProperty(0)
    average_mph = NumericProperty(0)
    temp = NumericProperty(0)
    dist_travel_2 = NumericProperty(0)

# screen 1: this is working ok
class Main_Screen(Screen):
    update_val = Show_Val()

    def update(self, dt):
        # these corresponds to the screen 1, their are currently working
        self.update_val.timer_update += 1
        self.update_val.dist_travel += 1 
        self.update_val.average_mph += 1

        # temp variable would be printed in screen 2: Input_Screen
        self.update_val.temp += 1

        # and dist_travel_2 will be printed in screen 3: Route_Screen
        self.update_val.dist_travel_2 += 1


# screen 2: here I need to get access to self.update_val.temp      
class Input_Screen(Screen):
    pass

# screen 3: here I need to get access to self.update_val.temp   
class Route_Screen(Screen):
    pass

# screen 0 or master screen management, it's just for reference
class Screen_Management(ScreenManager):
    pass

presentation = Builder.load_file("gui.kv")

class guiApp(App):
    def build(self):
        main = Main_Screen()

        # this call is my "loop" and is updating the variables at 50hz
        # frequency, I tried to call differently functions like this one
        # but with no success.
        Clock.schedule_interval(main.update, 1.0/50.0)
        return presentation

guiApp().run()

gui.kv

Screen_Management:
    id: screen_management
    transition: FadeTransition()
    Main_Screen:
        id: main_screen
        name: "main_screen_name"
        manager: screen_management
    Input_Screen:
        id: tire_setup_screen_id
        name: "tire_setup_screen_name"
        manager: screen_management
    Route_Screen:
        name: "route_input_screen_name"

##############################################################
##############################################################

# Screen 1: Main Screen
# working ok
<Main_Screen>:
    canvas:
        Color:
            rgb: [.30, .30, .30]
        Rectangle:
            pos: self.pos
            size: self.size

    BoxLayout:
        orientation: 'vertical'
        Button:
            id: timer_indicator
            background_disabled_down: ('0.00.00,000')
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: str(root.update_val.timer_update)
            #text: root.update_val.test
            pos_hint: {'x': .2}
            size_hint: [.8, 1]


        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: str(root.update_val.dist_travel)
            pos_hint: {'x': .2}
            size_hint: [.8, 1]
        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: str(root.update_val.average_mph)
            pos_hint: {'x': .2}
            size_hint: [.8, 1]

    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        size_hint: .2, 1
        pos_hint: {"x": 0, "center_y": .5}
        on_release: app.root.current = "tire_setup_screen_name"
        text: " INPUTS "
        font_size: 30

##############################################################
##############################################################

# Screen 2: Input Screen
# I will need to print self.update_val.temp value in this creen

<Input_Screen>:
    canvas:
        Color:
            rgb: [.30, .30, .30]
        Rectangle:
            pos: self.pos
            size: self.size
    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        font_size: 30
        size_hint: 0.2, .5
        text: "MAIN"
        pos_hint: {'x':0, 'y': 0}
        on_release: app.root.current = "main_screen_name"
    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        font_size: 30
        size_hint: .2, .5
        text: "ROUTES"
        pos_hint: {'x':0, 'y': .5}
        on_release: app.root.current = "route_input_screen_name"  

    GridLayout:
        cols: 2
        pos: (205,150)
        size_hint: (.8, .75)

        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 30
            text: "     TIRE\nTEMP (°C)"
            size_hint_x: None
            width: 150
        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: "000.000" # self.update_val.temp value it will be here

##############################################################
##############################################################

# Screen 3: Route Screen
# self.update_val.dist_travel_2 will be printed in this screen
<Route_Screen>:
    canvas:
        Color:
            rgb: [.30, .30, .30]
        Rectangle:
            pos: self.pos
            size: self.size

    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        font_size: 30
        size_hint: 0.2, .5
        text: "INPUTS"
        pos_hint: {'x':0, 'y': 0}
        on_release: app.root.current = "tire_setup_screen_name"

    BoxLayout:
        orientation: 'vertical'
        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 50
            text: "000.000 MPH" # self.update_val.dist_travel_2 value 
            pos_hint: {'x': .2}
            size_hint: [.8, 1]

感谢您的时间,我希望您能帮助我解决这个问题。

如何从其他类中的一个方法访问变量?

1 个答案:

答案 0 :(得分:0)

使用Kivy ObjectProperty连接到屏幕ID。有关详细信息,请参阅以下示例。

片段

Python脚本

class Screen_Management(ScreenManager):
    main_screen = ObjectProperty(None)
    input_screen = ObjectProperty(None)
    route_screen = ObjectProperty(None)

...

class Main_Screen(Screen):
    update_val = Show_Val()

    def update(self, dt):
        # these corresponds to the screen 1, their are currently working
        self.update_val.timer_update += 1
        self.update_val.dist_travel += 1
        self.update_val.average_mph += 1

        # temp variable would be printed in screen 2: Input_Screen
        self.update_val.temp += 1
        self.manager.input_screen.access_update_val(self.update_val)
        self.manager.route_screen.access_update_val(self.update_val)

        # and dist_travel_2 will be printed in screen 3: Route_Screen
        self.update_val.dist_travel_2 += 1

kv文件

<Screen_Management>:
    id: screen_management
    main_screen: main_screen
    input_screen: tire_setup_screen_id
    route_screen: route_screen
    transition: FadeTransition()
    Main_Screen:
        id: main_screen
        name: "main_screen_name"
        manager: screen_management
    Input_Screen:
        id: tire_setup_screen_id
        name: "tire_setup_screen_name"
        manager: screen_management
    Route_Screen:
        id: route_screen
        name: "route_input_screen_name"

实施例

gui2.py

from kivy.app import App
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.properties import ObjectProperty, NumericProperty
from kivy.clock import Clock


# Creating dynamic variables
class Show_Val(Screen):
    timer_update = NumericProperty(0)
    dist_travel = NumericProperty(0)
    average_mph = NumericProperty(0)
    temp = NumericProperty(0)
    dist_travel_2 = NumericProperty(0)


# screen 1: this is working ok
class Main_Screen(Screen):
    update_val = Show_Val()

    def update(self, dt):
        # these corresponds to the screen 1, their are currently working
        self.update_val.timer_update += 1
        self.update_val.dist_travel += 1
        self.update_val.average_mph += 1

        # temp variable would be printed in screen 2: Input_Screen
        self.update_val.temp += 1
        self.manager.input_screen.access_update_val(self.update_val)
        self.manager.route_screen.access_update_val(self.update_val)

        # and dist_travel_2 will be printed in screen 3: Route_Screen
        self.update_val.dist_travel_2 += 1


# screen 2: here I need to get access to self.update_val.temp
class Input_Screen(Screen):
    def access_update_val(self, obj):
        print("Input_Screen: update_val.temp={}".format(obj.temp))


# screen 3: here I need to get access to self.update_val.temp
class Route_Screen(Screen):
    def access_update_val(self, obj):
        print("Route_Screen: update_val.temp={}".format(obj.temp))


# screen 0 or master screen management, it's just for reference
class Screen_Management(ScreenManager):
    main_screen = ObjectProperty(None)
    input_screen = ObjectProperty(None)
    route_screen = ObjectProperty(None)


class gui2App(App):
    def build(self):
        sm = Screen_Management()

        # this call is my "loop" and is updating the variables at 50hz
        # frequency, I tried to call differently functions like this one
        # but with no success.
        Clock.schedule_interval(sm.main_screen.update, 1.0/50.0)
        return sm


if __name__ == "__main__":
    gui2App().run()

gui2.kv

#:kivy 1.10.0
#:import FadeTransition kivy.uix.screenmanager.FadeTransition

<Screen_Management>:
    id: screen_management
    main_screen: main_screen
    input_screen: tire_setup_screen_id
    route_screen: route_screen
    transition: FadeTransition()
    Main_Screen:
        id: main_screen
        name: "main_screen_name"
        manager: screen_management
    Input_Screen:
        id: tire_setup_screen_id
        name: "tire_setup_screen_name"
        manager: screen_management
    Route_Screen:
        id: route_screen
        name: "route_input_screen_name"

##############################################################
##############################################################

# Screen 1: Main Screen
# working ok
<Main_Screen>:
    canvas:
        Color:
            rgb: [.30, .30, .30]
        Rectangle:
            pos: self.pos
            size: self.size

    BoxLayout:
        orientation: 'vertical'
        Button:
            id: timer_indicator
            background_disabled_down: ('0.00.00,000')
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: str(root.update_val.timer_update)
            #text: root.update_val.test
            pos_hint: {'x': .2}
            size_hint: [.8, 1]


        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: str(root.update_val.dist_travel)
            pos_hint: {'x': .2}
            size_hint: [.8, 1]
        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: str(root.update_val.average_mph)
            pos_hint: {'x': .2}
            size_hint: [.8, 1]

    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        size_hint: .2, 1
        pos_hint: {"x": 0, "center_y": .5}
        on_release: app.root.current = "tire_setup_screen_name"
        text: " INPUTS "
        font_size: 30

##############################################################
##############################################################

# Screen 2: Input Screen
# I will need to print self.update_val.temp value in this creen

<Input_Screen>:
    canvas:
        Color:
            rgb: [.30, .30, .30]
        Rectangle:
            pos: self.pos
            size: self.size
    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        font_size: 30
        size_hint: 0.2, .5
        text: "MAIN"
        pos_hint: {'x':0, 'y': 0}
        on_release: app.root.current = "main_screen_name"
    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        font_size: 30
        size_hint: .2, .5
        text: "ROUTES"
        pos_hint: {'x':0, 'y': .5}
        on_release: app.root.current = "route_input_screen_name"

    GridLayout:
        cols: 2
        pos: (205,150)
        size_hint: (.8, .75)

        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 30
            text: "     TIRE\nTEMP (°C)"
            size_hint_x: None
            width: 150
        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 100
            text: "000.000" # self.update_val.temp value it will be here

##############################################################
##############################################################

# Screen 3: Route Screen
# self.update_val.dist_travel_2 will be printed in this screen
<Route_Screen>:
    canvas:
        Color:
            rgb: [.30, .30, .30]
        Rectangle:
            pos: self.pos
            size: self.size

    Button:
        background_color: .52, .52, .52, 1
        bold: 1
        color: .0078,.67,.69,1
        font_size: 30
        size_hint: 0.2, .5
        text: "INPUTS"
        pos_hint: {'x':0, 'y': 0}
        on_release: app.root.current = "tire_setup_screen_name"

    BoxLayout:
        orientation: 'vertical'
        Button:
            background_color: .52, .52, .52, 1
            bold: 1
            color: .0078,.67,.69,1
            font_size: 50
            text: "000.000 MPH" # self.update_val.dist_travel_2 value
            pos_hint: {'x': .2}
            size_hint: [.8, 1]

输出

enter image description here