Kivy发出意外的语法错误'仅适用于动态类的第一个实例

时间:2017-01-06 11:54:12

标签: android python kivy kivy-language

我尝试使用Dynamic Class使我的Kivy应用中的所有文本输入都经历相同的验证回调。这是示例代码:

from kivy.app import App
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.lang import Builder

kv = '''
<smRoot>:
    SignUpScreen:
<signupText@TextInput>:
    font_size: '15sp'
    on_text_validate: app.callback1()
    multiline: False

<SignUpScreen>:
    font_size:'50sp'
    name:'signupscreen'
    canvas:
        Color:
            rgb: (0.09,0.65,0.8)
        Rectangle:
            pos: self.pos
            size: self.size
    BoxLayout:
        size_hint: (.75, .5)
        pos_hint: {'center_x': .5, 'center_y': .5}
        orientation: 'vertical'
        signupText:
            hint_text: 'Full Name'
        signupText:
            hint_text: 'Mobile Number'
        signupText:
            hint_text: 'Enter Password'
        signupText:
            hint_text: 'Re-Enter Password'
        Button:
            text: 'Sign Up'
            disabled: True
'''

Builder.load_string(kv)
class smRoot(ScreenManager):
    pass

class SignUpScreen(Screen):
    pass

class myApp(App):
    def build(self):
        smroot = smRoot()
        return smroot

    def callback1(self):
        print 'In Validation Callback'
if __name__ == '__main__':
    myApp().run()

这会引发以下错误:

Traceback (most recent call last):
   File "/home/user/Workspace1/ScratchArea/Scratch.py", line 39, in <module>
     Builder.load_string(kv)
   File "/usr/lib/python2.7/dist-packages/kivy/lang.py", line 1491, in load_string
     parser = Parser(content=string, filename=fn)
   File "/usr/lib/python2.7/dist-packages/kivy/lang.py", line 1049, in __init__
     self.parse(content)
   File "/usr/lib/python2.7/dist-packages/kivy/lang.py", line 1126, in parse
     rule.precompile()
   File "/usr/lib/python2.7/dist-packages/kivy/lang.py", line 917, in precompile
     x.precompile()
   File "/usr/lib/python2.7/dist-packages/kivy/lang.py", line 913, in precompile
     x.precompile()
   File "/usr/lib/python2.7/dist-packages/kivy/lang.py", line 843, in precompile
     self.co_value = compile(value, self.ctx.filename or '<string>', mode)
   File "<string>", line 29
     hint_text: 'Re-Enter Password'
              ^
 SyntaxError: invalid syntax

令人惊讶的是,当我将<{> 1} signupText类的第一个实例更改为父TextInput时,它可以正常工作:

BoxLayout:
    size_hint: (.75, .5)
    pos_hint: {'center_x': .5, 'center_y': .5}
    orientation: 'vertical'
    TextInput:
        hint_text: 'Full Name'
    signupText:
        hint_text: 'Mobile Number'
    signupText:
        hint_text: 'Enter Password'
    signupText:
        hint_text: 'Re-Enter Password'
    Button:
        text: 'Sign Up'
        disabled: True

通过这个小的更改,不再抛出语法错误。但是在这种情况下,回调当然只适用于最后三个TextInput框...!

在动态类可以继承之前,Kivy是否需要将父类实例化一次?或者我的代码中有错误吗?在这方面的任何帮助/指示/建议将不胜感激......!

1 个答案:

答案 0 :(得分:4)

在Kv语言中,窗口小部件名称必须以大写字母开头。

您必须将signupText命名为SignupText。见How to duplicate blocks of widgets in kv file (lowercase-only rule)

from kivy.app import App
from kivy.uix.screenmanager import ScreenManager, Screen
from kivy.lang import Builder

kv = '''
<SmRoot>:
    SignUpScreen:
<SignupText@TextInput>:
    font_size: '15sp'
    on_text_validate: app.callback1()
    multiline: False

<SignUpScreen>:
    font_size:'50sp'
    name:'signupscreen'
    canvas:
        Color:
            rgb: (0.09,0.65,0.8)
        Rectangle:
            pos: self.pos
            size: self.size
    BoxLayout:
        size_hint: (.75, .5)
        pos_hint: {'center_x': .5, 'center_y': .5}
        orientation: 'vertical'
        SignupText:
            hint_text: 'Full Name'
        SignupText:
            hint_text: 'Mobile Number'
        SignupText:
            hint_text: 'Enter Password'
        SignupText:
            hint_text: 'Re-Enter Password'
        Button:
            text: 'Sign Up'
            disabled: True
'''

Builder.load_string(kv)
class smRoot(ScreenManager):
    pass

class SignUpScreen(Screen):
    pass

class myApp(App):
    def build(self):
        smroot = smRoot()
        return smroot

    def callback1(self):
        print('In Validation Callback')
if __name__ == '__main__':
    myApp().run()





    Builder.load_string(kv)
    class SmRoot(ScreenManager):
        pass

    class SignUpScreen(Screen):
        pass

    class myApp(App):
        def build(self):
            smroot = SmRoot()
            return smroot

        def callback1(self):
            print('In Validation Callback')
    if __name__ == '__main__':
        myApp().run()