【问题标题】:Kivy multiple screen managementKivy多屏管理
【发布时间】:2019-05-14 16:30:29
【问题描述】:

我对 Kivy 很陌生(两天前开始学习它)我正在研究一个基本的计算器,但遇到了一个我无法跳过的障碍。
我想创建多个屏幕,因为我打算在我的计算器中添加更多内容,因为我正在进一步学习 Kivy 并且我不知道如何在我的代码中调整 ScreenManager。

这是我的 .py 文件

import kivy

kivy.require('1.11.0')
from kivy.app import App
from kivy.uix.gridlayout import GridLayout
from kivy.uix.pagelayout import PageLayout
from kivy.core.window import Window

Window.clearcolor = .3,.3,.3,1

class RootWidget(GridLayout):   
    def calculate(self, calculation):
        if calculation:
            try:
                self.display.text = str(eval(calculation))
            except Exception:
            self.display.text = "Error"
class kutuApp(App):
    def build(self):
        return RootWidget()
if __name__== '__main__':
    kutuApp().run()

这是我的 .kv 文件

<CustButton@Button>:
    font_size: 35
    background_color: 0,0,0,0
    canvas.before:
        Color:
            rgba: (.4, .4, .4, 1) if self.state=='normal' else (0,.7,.7,1)
        RoundedRectangle:
            pos: self.pos
            size: self.size
            radius: [20, ]

<RawLayout@BoxLayout>:
     spacing: 8
     padding: 8
      size_hint: [1, .2]

<RootWidget>:
       id: calculator
      rows: 10
       display: entry
       spacing: 1

BoxLayout:
    size_hint: [1, .1]
    Label:
        text: 'Basic Calculator'
    Label:
        text: 'Made by Xrew'

BoxLayout:
    padding: 10
    TextInput:
        id: entry
        spacing: 1
        padding: 5
        font_size: 32
        multiline: True
        focus: False
#       background_color: 0, 0, 0, 1
#       foreground_color: [1, 0, 1, 1]

RawLayout:
    CustButton:
        text: '<'
        on_press: entry.text += self.text
    CustButton:
        text: '>'
        on_press: entry.text += self.text
    CustButton:
        text: '≈'
        on_press: entry.text += '=='                

RawLayout:
    orientation: 'horizontal'
    CustButton:
        text: '('
        on_press: entry.text += '('
    CustButton: 
        text: ')'
        on_press: entry.text += ')'
    CustButton:
        text: '√'
        on_press: entry.text += '**(.5)'
    CustButton:
        text: '¹/x' 
        on_press: entry.text += '1/'
RawLayout:
    orientation: 'horizontal'
    CustButton:
        text: 'Del'
        on_press: entry.text = entry.text[:-1]
    CustButton:
        text: 'x²'
        on_press: entry.text += '**2'
    CustButton:
        text: 'xⁿ'
        on_press: entry.text += '**'
    CustButton:
        text: 'π'
        on_press: entry.text += '3.14'

RawLayout:
    orientation: 'horizontal'       
    cols: 4    
    CustButton:
        text: 'Clr'
        font_color: [255,0,0,1]
 #       background_normal: ' '
    #    background_color: 1, .3, .4, .85
        on_press: entry.text = ""
    CustButton:
        text: '+'
        on_press: entry.text += self.text
        font_size: 32
    CustButton:
        text: '÷'
        on_press: entry.text += '/'
    CustButton:
        text: '×'
        on_press: entry.text += '*'

RawLayout:
    rows: 1   
    orientation: 'horizontal'
    CustButton:
        text: '7'
        on_press: entry.text += self.text
    CustButton:
        text: '8'
        on_press: entry.text += self.text
    CustButton:
        text: '9'
        on_press: entry.text += self.text
    CustButton:
        text: '-'
        on_press: entry.text += self.text

RawLayout:
    orientation: 'horizontal'
    rows: 1
    CustButton:
        text: '4'
        on_press: entry.text += self.text
    CustButton:
        text: '5'
        on_press: entry.text += self.text
    CustButton:
        text: '6'
        on_press: entry.text += self.text
    CustButton:
        text: '+'
        on_press: entry.text += self.text   

RawLayout:
    orientation: 'horizontal'
    cols: 3
    CustButton:
        text: '1'
        size_hint: [.5, 1]
        on_press: entry.text += self.text
    CustButton:
        text: '2'
        size_hint: [.5, 1]
        on_press: entry.text += self.text
    CustButton:
        text: '3'
        size_hint: [.5, 1]
        on_press: entry.text += self.text
    CustButton:
        text: ' '
        size_hint: [.5, 1]
        background_normal: ' '
        background_color: 0, 0, 0, 0

RawLayout:
    orientation: 'horizontal'
    size_hint: [1, .2]
    CustButton:
        text: '0'
        on_press: entry.text += self.text
        size_hint: [.34, 1]
    CustButton:
        text: '.'
        on_press: entry.text += self.text
        size_hint: [.17, 1]
        font_size: 32
    CustButton:
        text: '='
        on_press: calculator.calculate(entry.text)
        size_hint: [.17, 2.4]
#       background_normal: ' '
    #   background_color:  0, .5, 95, 1

【问题讨论】:

  • 请不要介意我在这里发布的缩进对我来说并不容易

标签: python kivy


【解决方案1】:

Kivy ScreenManager

以下步骤说明了如何使用ScreenManagerScreenButton 小部件以及Button 的事件之一(on_releaseon_press)扩展 Kivy 应用程序。

Py 文件

  1. 添加导入语句,from kivy.uix.screenmanager import ScreenManager, Screen
  2. 声明一个继承 ScreenManager 的类,例如class ScreenManagement(ScreenManager):
  3. 声明两个继承 Screen 的类,例如class MenuScreen(Screen):class CalculatorScreen(Screen):
  4. 添加 pass 作为三个新类的主体,因为我们将使用 kv 语言来设计它们的视图/演示。
  5. return RootWidget() 替换为return ScreenManagement(),因为现在应用的根目录是Kivy ScreenManager
  6. class RootWidget 重命名为class Calculator

片段 - py

from kivy.uix.screenmanager import ScreenManager, Screen

...

class Calculator(GridLayout):
    ...    


class MenuScreen(Screen):
    pass


class CalculatorScreen(Screen):
    pass


class ScreenManagement(ScreenManager):
    pass


class kutuApp(App):
    def build(self):
        return ScreenManagement()

kv 文件

  1. 在Python脚本中分别声明class rules&lt;MenuScreen&gt;:&lt;CalculatorScreen&gt;:&lt;ScreenManagement&gt;:,分别对应class MenuScreen(Screen):class CalculatorScreen(Screen):class ScreenManagement(ScreenManager):
  2. RootWidget 重命名为Calculator
  3. Calculator: 实例化为类规则的子级,&lt;CalculatorScreen&gt;:
  4. MenuScreen:CalculatorScreen: 实例化为类规则的子级&lt;ScreenManagement&gt;:
  5. name 分别赋予MenuScreen:CalculatorScreen: 作为name: 'menu'name: 'calculator'。这将使我们能够在切换屏幕时引用它们。

片段 - kv

<ScreenManagement>:
    MenuScreen:
        name: 'menu'
    CalculatorScreen:
        name: 'calculator'

<MenuScreen>:
    BoxLayout:
        Button:
            text: 'Goto Calculator'
            on_press: root.manager.current = 'calculator'
        Button:
            text: 'Quit'

<CalculatorScreen>:
    Calculator:

...
<Calculator>:
    id: calculator

示例

main.py

​​>
from kivy.app import App
from kivy.uix.gridlayout import GridLayout
from kivy.core.window import Window
from kivy.lang import Builder
from kivy.uix.screenmanager import ScreenManager, Screen


Window.clearcolor = .3, .3, .3, 1


class Calculator(GridLayout):
    def calculate(self, calculation):
        if calculation:
            try:
                self.display.text = str(eval(calculation))
            except Exception:
                self.display.text = "Error"


class MenuScreen(Screen):
    pass


class CalculatorScreen(Screen):
    pass


class ScreenManagement(ScreenManager):
    pass


Builder.load_file("main.kv")


class kutuApp(App):
    def build(self):
        return ScreenManagement()


if __name__ == '__main__':
    kutuApp().run()

main.kv

<ScreenManagement>:
    MenuScreen:
        name: 'menu'
    CalculatorScreen:
        name: 'calculator'

<MenuScreen>:
    BoxLayout:
        Button:
            text: 'Goto Calculator'
            on_press: root.manager.current = 'calculator'
        Button:
            text: 'Quit'

<CalculatorScreen>:
    Calculator:

<CustButton@Button>:
    font_size: 35
    background_color: 0,0,0,0
    canvas.before:
        Color:
            rgba: (.4, .4, .4, 1) if self.state=='normal' else (0,.7,.7,1)
        RoundedRectangle:
            pos: self.pos
            size: self.size
            radius: [20, ]

<RawLayout@BoxLayout>:
    spacing: 8
    padding: 8
    size_hint: [1, .2]

<Calculator>:
    id: calculator
    rows: 10
    display: entry
    spacing: 1

    BoxLayout:
        size_hint: [1, .1]
        Label:
            text: 'Basic Calculator'
        Label:
            text: 'Made by Xrew'

    BoxLayout:
        padding: 10
        TextInput:
            id: entry
            spacing: 1
            padding: 5
            font_size: 32
            multiline: True
            focus: False
    #       background_color: 0, 0, 0, 1
    #       foreground_color: [1, 0, 1, 1]

    RawLayout:
        CustButton:
            text: '<'
            on_press: entry.text += self.text
        CustButton:
            text: '>'
            on_press: entry.text += self.text
        CustButton:
            text: '≈'
            on_press: entry.text += '=='

    RawLayout:
        orientation: 'horizontal'
        CustButton:
            text: '('
            on_press: entry.text += '('
        CustButton:
            text: ')'
            on_press: entry.text += ')'
        CustButton:
            text: '√'
            on_press: entry.text += '**(.5)'
        CustButton:
            text: '¹/x'
            on_press: entry.text += '1/'
    RawLayout:
        orientation: 'horizontal'
        CustButton:
            text: 'Del'
            on_press: entry.text = entry.text[:-1]
        CustButton:
            text: 'x²'
            on_press: entry.text += '**2'
        CustButton:
            text: 'xⁿ'
            on_press: entry.text += '**'
        CustButton:
            text: 'π'
            on_press: entry.text += '3.14'

    RawLayout:
        orientation: 'horizontal'
        cols: 4
        CustButton:
            text: 'Clr'
            font_color: [255,0,0,1]
     #       background_normal: ' '
        #    background_color: 1, .3, .4, .85
            on_press: entry.text = ""
        CustButton:
            text: '+'
            on_press: entry.text += self.text
            font_size: 32
        CustButton:
            text: '÷'
            on_press: entry.text += '/'
        CustButton:
            text: '×'
            on_press: entry.text += '*'

    RawLayout:
        rows: 1
        orientation: 'horizontal'
        CustButton:
            text: '7'
            on_press: entry.text += self.text
        CustButton:
            text: '8'
            on_press: entry.text += self.text
        CustButton:
            text: '9'
            on_press: entry.text += self.text
        CustButton:
            text: '-'
            on_press: entry.text += self.text

    RawLayout:
        orientation: 'horizontal'
        rows: 1
        CustButton:
            text: '4'
            on_press: entry.text += self.text
        CustButton:
            text: '5'
            on_press: entry.text += self.text
        CustButton:
            text: '6'
            on_press: entry.text += self.text
        CustButton:
            text: '+'
            on_press: entry.text += self.text

    RawLayout:
        orientation: 'horizontal'
        cols: 3
        CustButton:
            text: '1'
            size_hint: [.5, 1]
            on_press: entry.text += self.text
        CustButton:
            text: '2'
            size_hint: [.5, 1]
            on_press: entry.text += self.text
        CustButton:
            text: '3'
            size_hint: [.5, 1]
            on_press: entry.text += self.text
        CustButton:
            text: ' '
            size_hint: [.5, 1]
            background_normal: ' '
            background_color: 0, 0, 0, 0

    RawLayout:
        orientation: 'horizontal'
        size_hint: [1, .2]
        CustButton:
            text: '0'
            on_press: entry.text += self.text
            size_hint: [.34, 1]
        CustButton:
            text: '.'
            on_press: entry.text += self.text
            size_hint: [.17, 1]
            font_size: 32
        CustButton:
            text: '='
            on_press: calculator.calculate(entry.text)
            size_hint: [.17, 2.4]
    #       background_normal: ' '
        #   background_color:  0, .5, 95, 1

输出

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多