如何创建一个从kivy中的文本文件中获取数据的更新列表
How to create an updating list that grabs data from a text file in kivy
所以现在我正在尝试在 kivy 应用程序中创建一个列表。该应用程序从文本文件中获取数据。文本文件在用户提交信息后接收新数据,我希望每次用户提交更多数据时更新列表。在这种情况下,数据是大学的名称。我一直在挖掘和挖掘这个问题的答案,但似乎无法弄清楚,我不断出错。此外,我对 python 中的编程(以及一般编程)还很陌生,这也是我的第一个 kivy 应用程序,所以请原谅我缺乏知识和愚蠢。下面我发布了我的 python 和 kivy 文件以及文本文件(以防万一)。请帮忙!
.py
from kivy.properties import ObjectProperty, ListProperty
from kivy.lang import Builder
from kivy.uix.screenmanager import ScreenManager, Screen
from database import DataBase
from kivy.app import App
from kivy.uix.recycleview import RecycleViewBehavior
class MainPage(Screen):
pass
class NewEntryPage(Screen, RecycleViewBehavior):
addschool = ObjectProperty(None)
costofsecondary = ObjectProperty(None)
addtravelexpenses = ObjectProperty(None)
ListOfSchools = ListProperty([])
def pressBtn(self):
newSchool = self.addschool.text
costOfSecondary = self.costofsecondary.text
addTravelExpense = self.addtravelexpenses.text
print("New School:", newSchool, "\nCost Of Secondary:", costOfSecondary, "\naddTravelExpense:", addTravelExpense, "\n", self.ListOfSchools)
if self.addschool.text != "" and self.costofsecondary.text != "" and self.addtravelexpenses.text != "":
db.add_school_and_secondary(self.addschool.text, self.costofsecondary.text, self.addtravelexpenses.text)
self.reset()
SchoolsAppliedToPage().updatelist("/Users/PycharmProjects/msft/schools.txt", self.ListOfSchools)
def reset(self):
self.addschool.text = ""
self.costofsecondary.text = ""
self.addtravelexpenses.text = ""
class SchoolsAppliedToPage(Screen):
rvlist = ObjectProperty(None)
ListOfSchools = NewEntryPage.ListOfSchools
def updatelist(self, filename, listofschools):
file = open(filename, "r")
for line in file:
school, cos, ate, space = line.strip().split(";")
listofschools.append(school)
self.rvlist.data.append([{'text': school} for school in listofschools])
print(listofschools)
print(self.ListOfSchools)
class WindowManager(ScreenManager):
pass
kv = Builder.load_file("msft.kv")
db = DataBase("/Users/PycharmProjects/msft/schools.txt")
class msftApp(App):
def build(self):
return kv
if __name__ == '__main__':
msftApp().run()
.kv
ScreenManager:
MainPage:
NewEntryPage:
SchoolsAppliedToPage:
<Button>
font_size:40
font_name: "/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.25, 0.075
color:0.969, 0.463, 0.333, 1
background_color: 0.17, 0.55, 0.92, 1
<MainPage>
name: "MainPage"
FloatLayout:
Widget:
canvas:
Color:
rgb:0.969, 0.463, 0.333, 1
Rectangle:
size:self.width, self.height
Color:
rgb:1, 1, 1, 1
Rectangle:
size:self.width * 0.95, self.height * 0.95
pos:root.center_x * 0.05, root.center_y * 0.05
Color:
rgb:0, 0.18, 0.361, 1
Rectangle:
size:self.width * 0.95, self.height / 10
pos:root.center_x * 0.05, root.center_y * 1.75
Image:
source:"/Users/Desktop/App_Files/doc.jpg"
size_hint:0.1, 0.1
pos_hint:{"x": 0.01, "top": 0.87}
Image:
source:"/Users/Desktop/App_Files/doc.jpg"
size_hint:0.1, 0.1
pos_hint:{"x": 0.895, "top": 0.87}
Button:
text:"Schools Applied to"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.45}
on_release:
app.root.current = "SchoolsAppliedToPage"
root.manager.transition.direction = "down"
Button:
text:"Add/Edit School"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.3}
on_release:
app.root.current = "NewEntryPage"
root.manager.transition.direction = "up"
Button:
text:"Add/Edit Travel"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.15}
on_release:
Label:
text:"Medical School is hard enough...let's try and save every penny that we can!"
size_hint:0.1, 0.1
pos_hint:{"x":0.45, "top":0.98}
font_name:"/Users/Desktop/App_Files/DancingScript-Regular.otf"
font_size: (root.width + root.height) / 70
color:0.97, 0.97, 0.97, 1
<NewEntryPage>
name:"NewEntryPage"
addschool:addschool
costofsecondary:cos
addtravelexpenses:ate
FloatLayout:
Widget:
canvas:
Color:
rgb: 0, 0.18, 0.361, 1
Rectangle:
size: self.width, self.height
Color:
rgb: 0.97, 0.97, 0.97, 1
Rectangle:
pos: 0, root.center_y * 1.75
size: self.width, self.height/8
Color:
rgb: 0.97, 0.97, 0.97, 1
Rectangle:
size: self.width * 0.9, self.height * 0.78
pos: root.center_x * 0.1, root.center_y * 0.1
Color:
rgb: 0, 0.18, 0.361, 1
Rectangle:
size: self.width * 0.72, self.height / 11
pos: root.center_x * 0.28, root.center_y * 1.78
Color:
rgb: 0.969, 0.463, 0.333, 1
Rectangle:
size: self.width * 0.7, self.height / 14
pos: root.center_x * 0.3, root.center_y * 1.80
Label:
font_name:"/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.3, 0.3
pos_hint:{"x":0.37, "top":0.93}
text:"Add School"
color:0.063, 0.024, 0.60, 1
TextInput:
id:addschool
size_hint:0.3, 0.1
pos_hint:{"x":0.37, "top": 0.75}
multinline:False
Label:
font_name:"/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.3, 0.3
pos_hint:{"x":0.37, "top":0.73}
text:"Cost Of Secondary"
color:0.063, 0.024, 0.60, 1
TextInput:
id:cos
size_hint:0.3, 0.1
pos_hint:{"x":0.37, "top": 0.55}
multinline:False
Label:
font_name:"/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.3, 0.3
pos_hint:{"x":0.37, "top":0.53}
text:"Add Travel Expenses"
color:0.063, 0.024, 0.60, 1
TextInput:
id:ate
size_hint:0.3, 0.1
pos_hint:{"x":0.37, "top": 0.35}
multinline:False
Button:
id:btn
text: "Submit" if btn.state == "normal" else "Done!"
pos_hint:{"x":0.395, "top":0.20}
on_press:root.pressBtn()
Image:
source:"/Users/Desktop/App_Files/med.png"
size_hint:0.1, 0.1
pos_hint:{"top": 0.99}
Image:
source:"/Users/Desktop/App_Files/med.png"
size_hint:0.1, 0.1
pos_hint:{"x":0.9, "top":0.99}
Label:
text:"Medical School is hard enough...let's try and save every penny that we can!"
size_hint:0.1, 0.1
pos_hint:{"x":0.45, "top":0.99}
font_name:"/Users/Desktop/App_Files/DancingScript-Regular.otf"
font_size: (root.width + root.height) / 70
color:0, 0.18, 0.361, 1
Button:
text:"Home"
pos_hint:{"x":0.13, "top":0.80}
size_hint:0.1, 0.05
on_release:
app.root.current = "MainPage"
root.manager.transition.direction = "down"
<SchoolsAppliedToPage>
name:"SchoolsAppliedToPage"
rvlist:rvlist
BoxLayout:
orientation: "vertical"
size_hint_y: 0.5
RecycleView:
id:rvlist
data:[{'text': school} for school in root.ListOfSchools]
viewclass:'Label'
RecycleGridLayout:
default_size: 100, 100
default_size_hint: 100, 100
size_hint_y:None
height: 500
orientation: 'vertical'
multiselect: True
touch_multiselect: True
cols: 4
Button:
text:"Home"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.75}
on_release:
app.root.current = "MainPage"
root.manager.transition.direction = "up"
.txt
Harvard;0;0;
应用程序运行并显示,但是当我尝试在用户提交后更新列表时出现此错误:ph = item.get('pos_hint', ph) AttributeError: 'list' object has no attribute 'get'
在 NewEntryPage
的 pressBtn()
方法中,行:
SchoolsAppliedToPage().updatelist("/Users/PycharmProjects/msft/schools.txt", self.ListOfSchools)
正在创建 SchoolsAppliedToPage
的新实例,并在该新实例上调用 updatelist()
。不幸的是,该新实例不是您 GUI 中的实例,因此该代码对您在屏幕上看到的内容没有影响。
尝试用以下内容替换该行:
satp = App.get_running_app().root.get_screen('SchoolsAppliedToPage')
satp.updatelist("/Users/PycharmProjects/msft/schools.txt", self.ListOfSchools)
此代码获取对 SchoolsAppliedToPage
实例的引用,然后对该实例调用 updatelist()
。
免责声明:我没有测试过上面的代码,但我相信它提出了正确的方法。
所以现在我正在尝试在 kivy 应用程序中创建一个列表。该应用程序从文本文件中获取数据。文本文件在用户提交信息后接收新数据,我希望每次用户提交更多数据时更新列表。在这种情况下,数据是大学的名称。我一直在挖掘和挖掘这个问题的答案,但似乎无法弄清楚,我不断出错。此外,我对 python 中的编程(以及一般编程)还很陌生,这也是我的第一个 kivy 应用程序,所以请原谅我缺乏知识和愚蠢。下面我发布了我的 python 和 kivy 文件以及文本文件(以防万一)。请帮忙!
.py
from kivy.properties import ObjectProperty, ListProperty
from kivy.lang import Builder
from kivy.uix.screenmanager import ScreenManager, Screen
from database import DataBase
from kivy.app import App
from kivy.uix.recycleview import RecycleViewBehavior
class MainPage(Screen):
pass
class NewEntryPage(Screen, RecycleViewBehavior):
addschool = ObjectProperty(None)
costofsecondary = ObjectProperty(None)
addtravelexpenses = ObjectProperty(None)
ListOfSchools = ListProperty([])
def pressBtn(self):
newSchool = self.addschool.text
costOfSecondary = self.costofsecondary.text
addTravelExpense = self.addtravelexpenses.text
print("New School:", newSchool, "\nCost Of Secondary:", costOfSecondary, "\naddTravelExpense:", addTravelExpense, "\n", self.ListOfSchools)
if self.addschool.text != "" and self.costofsecondary.text != "" and self.addtravelexpenses.text != "":
db.add_school_and_secondary(self.addschool.text, self.costofsecondary.text, self.addtravelexpenses.text)
self.reset()
SchoolsAppliedToPage().updatelist("/Users/PycharmProjects/msft/schools.txt", self.ListOfSchools)
def reset(self):
self.addschool.text = ""
self.costofsecondary.text = ""
self.addtravelexpenses.text = ""
class SchoolsAppliedToPage(Screen):
rvlist = ObjectProperty(None)
ListOfSchools = NewEntryPage.ListOfSchools
def updatelist(self, filename, listofschools):
file = open(filename, "r")
for line in file:
school, cos, ate, space = line.strip().split(";")
listofschools.append(school)
self.rvlist.data.append([{'text': school} for school in listofschools])
print(listofschools)
print(self.ListOfSchools)
class WindowManager(ScreenManager):
pass
kv = Builder.load_file("msft.kv")
db = DataBase("/Users/PycharmProjects/msft/schools.txt")
class msftApp(App):
def build(self):
return kv
if __name__ == '__main__':
msftApp().run()
.kv
ScreenManager:
MainPage:
NewEntryPage:
SchoolsAppliedToPage:
<Button>
font_size:40
font_name: "/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.25, 0.075
color:0.969, 0.463, 0.333, 1
background_color: 0.17, 0.55, 0.92, 1
<MainPage>
name: "MainPage"
FloatLayout:
Widget:
canvas:
Color:
rgb:0.969, 0.463, 0.333, 1
Rectangle:
size:self.width, self.height
Color:
rgb:1, 1, 1, 1
Rectangle:
size:self.width * 0.95, self.height * 0.95
pos:root.center_x * 0.05, root.center_y * 0.05
Color:
rgb:0, 0.18, 0.361, 1
Rectangle:
size:self.width * 0.95, self.height / 10
pos:root.center_x * 0.05, root.center_y * 1.75
Image:
source:"/Users/Desktop/App_Files/doc.jpg"
size_hint:0.1, 0.1
pos_hint:{"x": 0.01, "top": 0.87}
Image:
source:"/Users/Desktop/App_Files/doc.jpg"
size_hint:0.1, 0.1
pos_hint:{"x": 0.895, "top": 0.87}
Button:
text:"Schools Applied to"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.45}
on_release:
app.root.current = "SchoolsAppliedToPage"
root.manager.transition.direction = "down"
Button:
text:"Add/Edit School"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.3}
on_release:
app.root.current = "NewEntryPage"
root.manager.transition.direction = "up"
Button:
text:"Add/Edit Travel"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.15}
on_release:
Label:
text:"Medical School is hard enough...let's try and save every penny that we can!"
size_hint:0.1, 0.1
pos_hint:{"x":0.45, "top":0.98}
font_name:"/Users/Desktop/App_Files/DancingScript-Regular.otf"
font_size: (root.width + root.height) / 70
color:0.97, 0.97, 0.97, 1
<NewEntryPage>
name:"NewEntryPage"
addschool:addschool
costofsecondary:cos
addtravelexpenses:ate
FloatLayout:
Widget:
canvas:
Color:
rgb: 0, 0.18, 0.361, 1
Rectangle:
size: self.width, self.height
Color:
rgb: 0.97, 0.97, 0.97, 1
Rectangle:
pos: 0, root.center_y * 1.75
size: self.width, self.height/8
Color:
rgb: 0.97, 0.97, 0.97, 1
Rectangle:
size: self.width * 0.9, self.height * 0.78
pos: root.center_x * 0.1, root.center_y * 0.1
Color:
rgb: 0, 0.18, 0.361, 1
Rectangle:
size: self.width * 0.72, self.height / 11
pos: root.center_x * 0.28, root.center_y * 1.78
Color:
rgb: 0.969, 0.463, 0.333, 1
Rectangle:
size: self.width * 0.7, self.height / 14
pos: root.center_x * 0.3, root.center_y * 1.80
Label:
font_name:"/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.3, 0.3
pos_hint:{"x":0.37, "top":0.93}
text:"Add School"
color:0.063, 0.024, 0.60, 1
TextInput:
id:addschool
size_hint:0.3, 0.1
pos_hint:{"x":0.37, "top": 0.75}
multinline:False
Label:
font_name:"/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.3, 0.3
pos_hint:{"x":0.37, "top":0.73}
text:"Cost Of Secondary"
color:0.063, 0.024, 0.60, 1
TextInput:
id:cos
size_hint:0.3, 0.1
pos_hint:{"x":0.37, "top": 0.55}
multinline:False
Label:
font_name:"/Users/Desktop/App_Files/Antonio-Bold.ttf"
size_hint:0.3, 0.3
pos_hint:{"x":0.37, "top":0.53}
text:"Add Travel Expenses"
color:0.063, 0.024, 0.60, 1
TextInput:
id:ate
size_hint:0.3, 0.1
pos_hint:{"x":0.37, "top": 0.35}
multinline:False
Button:
id:btn
text: "Submit" if btn.state == "normal" else "Done!"
pos_hint:{"x":0.395, "top":0.20}
on_press:root.pressBtn()
Image:
source:"/Users/Desktop/App_Files/med.png"
size_hint:0.1, 0.1
pos_hint:{"top": 0.99}
Image:
source:"/Users/Desktop/App_Files/med.png"
size_hint:0.1, 0.1
pos_hint:{"x":0.9, "top":0.99}
Label:
text:"Medical School is hard enough...let's try and save every penny that we can!"
size_hint:0.1, 0.1
pos_hint:{"x":0.45, "top":0.99}
font_name:"/Users/Desktop/App_Files/DancingScript-Regular.otf"
font_size: (root.width + root.height) / 70
color:0, 0.18, 0.361, 1
Button:
text:"Home"
pos_hint:{"x":0.13, "top":0.80}
size_hint:0.1, 0.05
on_release:
app.root.current = "MainPage"
root.manager.transition.direction = "down"
<SchoolsAppliedToPage>
name:"SchoolsAppliedToPage"
rvlist:rvlist
BoxLayout:
orientation: "vertical"
size_hint_y: 0.5
RecycleView:
id:rvlist
data:[{'text': school} for school in root.ListOfSchools]
viewclass:'Label'
RecycleGridLayout:
default_size: 100, 100
default_size_hint: 100, 100
size_hint_y:None
height: 500
orientation: 'vertical'
multiselect: True
touch_multiselect: True
cols: 4
Button:
text:"Home"
size_hint:0.3,0.1
pos_hint:{"x":0.07, "top":0.75}
on_release:
app.root.current = "MainPage"
root.manager.transition.direction = "up"
.txt
Harvard;0;0;
应用程序运行并显示,但是当我尝试在用户提交后更新列表时出现此错误:ph = item.get('pos_hint', ph) AttributeError: 'list' object has no attribute 'get'
在 NewEntryPage
的 pressBtn()
方法中,行:
SchoolsAppliedToPage().updatelist("/Users/PycharmProjects/msft/schools.txt", self.ListOfSchools)
正在创建 SchoolsAppliedToPage
的新实例,并在该新实例上调用 updatelist()
。不幸的是,该新实例不是您 GUI 中的实例,因此该代码对您在屏幕上看到的内容没有影响。
尝试用以下内容替换该行:
satp = App.get_running_app().root.get_screen('SchoolsAppliedToPage')
satp.updatelist("/Users/PycharmProjects/msft/schools.txt", self.ListOfSchools)
此代码获取对 SchoolsAppliedToPage
实例的引用,然后对该实例调用 updatelist()
。
免责声明:我没有测试过上面的代码,但我相信它提出了正确的方法。