在不使用ID的情况下访问Kivy中的TextInput数据

发布于 2025-01-22 07:55:50 字数 2903 浏览 3 评论 0原文

在这里,我使用for-loop制作了一个装满输入箱的网格,并将它们添加到词典中以访问以后访问,因为我无法在Python文件中设置ID。现在,我正在尝试制作一个可以根据输入箱的数据进行基本计算的函数,但是我不知道如何在不使用ID的情况下传递该功能中的特定输入框。同样,on_text函数无法正常工作。我敢肯定我在这里错过了一些大事。任何指导将不胜感激。

from kivy.uix.textinput import TextInput
from kivy.uix.label import Label
from kivy.app import App
from kivy.uix.boxlayout import BoxLayout
from kivy.uix.gridlayout import GridLayout
from kivy.uix.stacklayout import StackLayout
from kivy.uix.scrollview import ScrollView
from kivy.uix.button import Button
from kivy.lang import Builder
from kivy.metrics import dp
from kivy.properties import StringProperty

Builder.load_file("gridtable.kv")

class MyBox(BoxLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        pass
class MyGrid(GridLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        self.cols=6
        self.textinputs = {}
        for i in range(48):
            key = i+1
            self.textinputs[key] = TextInput(multiline=False,font_size=dp(30),on_text=self.calc(key))
            self.add_widget(self.textinputs[key])
        
    def calc(self,key):
        print(self.textinputs[key])

        
class MyApp(App):
    def build(self):
        return MyBox()

if __name__ == "__main__":
    MyApp().run()        
<MyBox>:
    mygrid:my_grid
    orientation: "vertical"
    MyGrid:
        id: my_grid
        size_hint: 1,0.8
    BoxLayout:
        orientation: "horizontal"
        size_hint: 1,0.2
        BoxLayout:
            orientation: "vertical"
            Button: 
                text: "Expense Total:"
            Button: 
                text: "Revenue Total:"    
        Button:
            text: "Profit:"
            font_size: 40          
Traceback (most recent call last):
   File "c:\Users\jaika\OneDrive\Desktop\python\lil_curry_project\gridtable.py", line 38, in <module>
     MyApp().run()        

     print(self.textinputs[key])
 KeyError: 1
#better version of MyGrid()
class MyGrid(GridLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        self.cols=4
        self.textinputs = [0]
        self.expense = 0
        self.revenue = 0
        self.profit = 0
        for i in range(16):
            t = TextInput(multiline=False,text=str(i+1))
            t.bind(on_text_validate=self.calc_profit)
            self.textinputs.append(t)
            self.add_widget(t)
        
    def calc_profit(self,instance):
        index = self.textinputs.index(instance)
        if index == 1 or index == 2 or index == 5 or index == 6 or index == 9 or index == 10 or index == 13 or index == 14:
            self.expense += int(instance.text)
        else:
            self.revenue += int(instance.text)
        self.profit = self.revenue - self.expense
        print(self.profit)   


here i've made a grid full of inputboxes using for-loop and added them to a dictionary to access later since i couldn't set id's in the python file. Now i'm trying to make a function that will make basic calculations based on the inputbox's data but i do not know how i can pass particular inputboxes in that function without using id's. Also the on_text function isn't working as i expected. I'm sure i'm missing something big here. Any guidance is appreciated.

from kivy.uix.textinput import TextInput
from kivy.uix.label import Label
from kivy.app import App
from kivy.uix.boxlayout import BoxLayout
from kivy.uix.gridlayout import GridLayout
from kivy.uix.stacklayout import StackLayout
from kivy.uix.scrollview import ScrollView
from kivy.uix.button import Button
from kivy.lang import Builder
from kivy.metrics import dp
from kivy.properties import StringProperty

Builder.load_file("gridtable.kv")

class MyBox(BoxLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        pass
class MyGrid(GridLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        self.cols=6
        self.textinputs = {}
        for i in range(48):
            key = i+1
            self.textinputs[key] = TextInput(multiline=False,font_size=dp(30),on_text=self.calc(key))
            self.add_widget(self.textinputs[key])
        
    def calc(self,key):
        print(self.textinputs[key])

        
class MyApp(App):
    def build(self):
        return MyBox()

if __name__ == "__main__":
    MyApp().run()        
<MyBox>:
    mygrid:my_grid
    orientation: "vertical"
    MyGrid:
        id: my_grid
        size_hint: 1,0.8
    BoxLayout:
        orientation: "horizontal"
        size_hint: 1,0.2
        BoxLayout:
            orientation: "vertical"
            Button: 
                text: "Expense Total:"
            Button: 
                text: "Revenue Total:"    
        Button:
            text: "Profit:"
            font_size: 40          
Traceback (most recent call last):
   File "c:\Users\jaika\OneDrive\Desktop\python\lil_curry_project\gridtable.py", line 38, in <module>
     MyApp().run()        

     print(self.textinputs[key])
 KeyError: 1
#better version of MyGrid()
class MyGrid(GridLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        self.cols=4
        self.textinputs = [0]
        self.expense = 0
        self.revenue = 0
        self.profit = 0
        for i in range(16):
            t = TextInput(multiline=False,text=str(i+1))
            t.bind(on_text_validate=self.calc_profit)
            self.textinputs.append(t)
            self.add_widget(t)
        
    def calc_profit(self,instance):
        index = self.textinputs.index(instance)
        if index == 1 or index == 2 or index == 5 or index == 6 or index == 9 or index == 10 or index == 13 or index == 14:
            self.expense += int(instance.text)
        else:
            self.revenue += int(instance.text)
        self.profit = self.revenue - self.expense
        print(self.profit)   


如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

初雪 2025-01-29 07:55:50

您可以使用bind触发方法调用,也可以使用textInput中可用的事件(例如on_text_validate)。这是一个修改的mygrid类,它都使用:

class MyGrid(GridLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        self.cols = 6
        self.textinputs = {}
        for i in range(48):
            key = i + 1
            self.textinputs[key] = TextInput(multiline=False, font_size=dp(30), on_text_validate=self.abba)
            self.textinputs[key].bind(text=partial(self.calc, key))
            print('in init, key =', key)
            self.add_widget(self.textinputs[key])

    def abba(self, ti_instance):
        print('abba, textinput instance =', ti_instance, ', text =', ti_instance.text)

    def calc(self, key, ti_instance, text):
        print('calc:')
        print('key =', key, ', text =', text, ', textinput instance =', ti_instance)

请注意,bind to text> 中的文本中的每一个更改都会触发。 TextInputon_text_validate仅在用户命中Enter时才会触发。

You can use bind to trigger a method call, or use events available in the TextInput (like on_text_validate). Here is a modified MyGrid class that uses both:

class MyGrid(GridLayout):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        self.cols = 6
        self.textinputs = {}
        for i in range(48):
            key = i + 1
            self.textinputs[key] = TextInput(multiline=False, font_size=dp(30), on_text_validate=self.abba)
            self.textinputs[key].bind(text=partial(self.calc, key))
            print('in init, key =', key)
            self.add_widget(self.textinputs[key])

    def abba(self, ti_instance):
        print('abba, textinput instance =', ti_instance, ', text =', ti_instance.text)

    def calc(self, key, ti_instance, text):
        print('calc:')
        print('key =', key, ', text =', text, ', textinput instance =', ti_instance)

Note that the bind to text gets triggered with every change to the text in a TextInput. The on_text_validate will only be triggered when the user hits Enter.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文