如何创建一个动态kivy应用程序与复选框? [英] How to create a dynamic kivy app with checkboxes?

查看:174
本文介绍了如何创建一个动态kivy应用程序与复选框?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在为我的大学使用kivy和python做一个项目。我想要做一个主屏幕,您可以在其中选择一些字段,然后下一个屏幕将取决于您在主屏幕中选择的字段。使用kv语言做动态很难,因为我不知道太多关于使用kivy编程,所以我决定做像python编程,但它不工作。这里你有我的程序的代码:

 从kivy.app导入应用程序
从kivy.lang import Builder
从kivy.uix.screenmanager导入ScreenManager,屏幕
从kivy.uix.textinput导入TextInput
从kivy.uix.label导入标签
从kivy.uix.gridlayout import GridLayout
从kivy.uix.button导入按钮

Builder.load_string('''
< Root> ;:
MainScreen:
name:'main'
AnotherScreen:
name:'another'

< MainScreen> ;:
GridLayout:
cols:2
标签:
text:选择主题
font_size:15
标签:
text:
复选框:
on_active:root.ping('ch1')
标签:
文本:Termotecnia
复选框:
on_active:root.ping('ch2')
标签:
text: $ b复选框:
on_active:root.ping('ch3')
标签:
text:Termotcnia
复选框:
on_active:root.ping ch4')
标签:
text:Control
按钮:
text:Exit
background_color:.7,.7,6,1
on_release:root.parent.current ='another'
Button:
text:Run
font_size:24
background_color:.7,.7,1,1
on_release:root.parent.current ='another'


''')


类MainScreen b $ b def __init __(self,** kw):
super(MainScreen,self).__ init __(** kw)
self.a = App.get_running_app()
self.e = {}
def ping(self,n):
if self.a.big_dict [n] =='False':
self.a.big_dict [n] ='True'
else:
self.a.big_dict [n] ='False'
print self.a.big_dict
self.e = self.a.big_dict

class AnotherScreen(GridLayout):
def __init __(self,** kw):
super(AnotherScreen,self).__ init __(** kw)
t = []
self.i = MainScreen()
self.cols = 2
self.add_widget(Button(text ='Assignatura',background_color = [0,1,1,1]))
self.add_widget(Button(background_color = [0,1,1,1],text ='Escriu Grup'))
for k in self.ie:
if self.ie [k] == 'True':
self.add_widget(Label(text = k))
self.k = TextInput(multiline = False)
t.append(self.k.text)
self.add_widget(self.k)
else:
pass
b1 = Button(text ='Exit',background_color = [0,1,0,1])$ ​​b $ b self.add_widget(b1)
b2 = Button(text ='Run',background_color = [0,1,0,1])$ ​​b $ b self.add_widget(b2)
b1.bind on_press = exit)


class Root(ScreenManager):
pass
class SimpleKivy(App):
big_dict = {'ch1':'False ','ch2':'False','ch3':'False','ch4':'False'}
def build(self):
返回Root()
SimpleKivy ).run()


$ b $ p此代码不起作用,因为 ScreenManager 仅适用于屏幕,而不适用于 GridLayout (第一个问题)。 big_dict 保存复选框的数据,但是当我尝试导入到另一个类时,它不工作(另一个问题)。如果有人知道这些问题的答案,这将是非常有益的,因为我知道如何做。 13个字段总是,但我想用预选,因为有太多的字段(在这个程序只有4,但有14)。

解决方案

从哪里开始...
首先,让我们看看 SimpleKivy 。您可能想让 big_dict a DictProperty ,而不是类属性:

  class SimpleKivy(App):
big_dict = DictProperty({'ch1':False,'ch2':False,'ch3':False,'ch4 ':False})



我还将值更改为布尔值,因为这将更有用



然后,我们为 AnotherScreen 添加另一个规则到kv字符串:

 < AnotherScreen>:
GridLayout:
id:container
cols:2

这样,我们可以通过 id 来引用实际的布局。 p>

我们也更改 ping 的定义:

  def ping(self,n,value):
self.a.big_dict [n] = value

当我们还改变 kv 字符串中的 CheckBox

 复选框:
on_active:root.ping('ch1',self.active)

复选框的状态将被直接传递到应用程序实例中的字典。 (或者,如果您不需要 ping 用于其他操作,则可以简化为 on_active:app.big_dict ['ch3'] = self .active



最后, AnotherScreen 的定义:

  class AnotherScreen(Screen):
def on_pre_enter(self,* args):
t = []
a = App.get_running_app()
self.ids.container.add_widget(Button(text ='Assignatura',background_color = [0,1,1,1]))
self.ids.container.add_widget a.big_dict.iteritems()中的k,v按钮(background_color = [0,1,1,1],text ='Escriu Grup'))
如果v:
self.ids.container.add_widget(Label(text = k))
self.k = TextInput(multiline = False)
t.append(self.k.text)
self.ids .container.add_widget(self.k)
b1 = Button(text ='Exit',background_color = [0,1,0,1])$ ​​b $ b self.ids.container.add_widget(b1)
b2 = Button(text ='Run',background_color = [0,1,0,1])$ ​​b $ b self.ids.container.add_widget(b2)
b1.bind(on_press = exit )

这是在输入屏幕之前调用的,会直接从应用程序实例获取字典无需引用 MainScreen ),并遍历所述字典。


I'm doing a project for my university using kivy and python. I want to do a main screen where you can select some fields, and then the next screen will depend on the fields you have selected in the main screen. Doing dynamic with kv language is difficult to me because I don't know too much about programming with kivy, so i have decided to do like python programming but it doesn't work. Here you have the code of my program:

from kivy.app import App
from kivy.lang import Builder
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.uix.textinput import TextInput
from kivy.uix.label import Label
from kivy.uix.gridlayout import GridLayout
from kivy.uix.button import Button

Builder.load_string('''
<Root>:
    MainScreen:
        name: 'main'
    AnotherScreen:
        name: 'another'

<MainScreen>:
    GridLayout:
        cols: 2
        Label:
            text: "Select Subjects"
            font_size: 15
        Label:
            text: " "
        CheckBox:
            on_active:root.ping('ch1')
        Label:
            text: "Termotecnia"
        CheckBox:
            on_active:root.ping('ch2')
        Label:
            text: "Control"
        CheckBox:
            on_active:root.ping('ch3')
        Label:
            text: "Termotcnia"
        CheckBox:
            on_active:root.ping('ch4')
        Label:
            text: "Control"
        Button:
            text: "Exit"
            background_color: .7, .7, 6, 1
            on_release:root.parent.current='another'
        Button:
            text: "Run"
            font_size: 24
            background_color: .7, .7, 1, 1
            on_release: root.parent.current='another'


''')


class MainScreen(Screen):
    def __init__(self, **kw):
        super(MainScreen, self).__init__(**kw)
        self.a = App.get_running_app()
        self.e={}
    def ping(self,n):
        if self.a.big_dict[n]=='False':
            self.a.big_dict[n]='True'
        else: 
            self.a.big_dict[n]='False'
        print self.a.big_dict
        self.e=self.a.big_dict

class AnotherScreen(GridLayout):
    def __init__(self, **kw):
        super(AnotherScreen, self).__init__(**kw)
        t=[] 
        self.i=MainScreen()
        self.cols=2
        self.add_widget(Button(text='Assignatura',background_color=[0,1,1,1]))
        self.add_widget(Button(background_color=[0,1,1,1],text='Escriu Grup'))
        for k in self.i.e:
            if self.i.e[k]=='True':
                self.add_widget(Label(text=k))
                self.k=TextInput(multiline=False)
                t.append(self.k.text)
                self.add_widget(self.k)
            else:
                pass
        b1=Button(text='Exit',background_color=[0,1,0,1])
        self.add_widget(b1)
        b2=Button(text='Run',background_color=[0,1,0,1])
        self.add_widget(b2)
        b1.bind(on_press=exit)


class Root(ScreenManager):
    pass
class SimpleKivy(App):
    big_dict={'ch1':'False','ch2':'False','ch3':'False','ch4':'False'}
    def build(self):
        return Root()
SimpleKivy().run()

This code doesn't work because ScreenManager only works with a Screen, not with a GridLayout (first problem). The big_dict save the data of the checkboxes, but when I try to import to another class, it doesn't work (another problem). If anyone knows the answer to these problems it would be very helpful, because I know how to do with e.g. 13 fields always, but I want to do with a preselection, because there are too many fields (in this program only 4, but there are 14).

解决方案

Where to start... First, let's look at SimpleKivy. You probably want to make big_dict a DictProperty, instead of a class attribute:

class SimpleKivy(App):
    big_dict = DictProperty({'ch1':False,'ch2':False,'ch3':False,'ch4':False})

I've also changed the values to booleans, because that will be more useful later.

Then, let's add another rule for AnotherScreen to the kv string:

<AnotherScreen>:
    GridLayout:
        id: container
        cols: 2

This way, we can refer to the actual layout by its id.

We also change the definition of ping:

def ping(self, n, value):
    self.a.big_dict[n] = value

When we then also change the CheckBoxes in the kv string to

CheckBox:
    on_active:root.ping('ch1', self.active)

the state of the checkbox will be directly transferred to the dictionary in the app instance. (Alternatively, if you don't need ping for other things, this could be simplified to on_active: app.big_dict['ch3'] = self.active)

Finally, the definition of AnotherScreen:

class AnotherScreen(Screen):
    def on_pre_enter(self, *args):
        t=[] 
        a = App.get_running_app()
        self.ids.container.add_widget(Button(text='Assignatura',background_color=[0,1,1,1]))
        self.ids.container.add_widget(Button(background_color=[0,1,1,1],text='Escriu Grup'))
        for k,v in a.big_dict.iteritems():
            if v:
                self.ids.container.add_widget(Label(text=k))
                self.k=TextInput(multiline=False)
                t.append(self.k.text)
                self.ids.container.add_widget(self.k)
        b1=Button(text='Exit',background_color=[0,1,0,1])
        self.ids.container.add_widget(b1)
        b2=Button(text='Run',background_color=[0,1,0,1])
        self.ids.container.add_widget(b2)
        b1.bind(on_press=exit)

This is called before the screen is entered, will get the dictionary directly from the app instance (so no need to refer to MainScreen), and iterate over said dictionary.

这篇关于如何创建一个动态kivy应用程序与复选框?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆