我正在使用kivy和buildozer构建一个android应用。应用程序启动时崩溃,我发现此TypeError。因此,我使用logcat来获取日志,因此在追溯到某些行之后会出现此错误。我正在使用Kivy 1.9.0和Python 2.7.9,有没有办法解决这个问题?请告诉我如何解决此问题。谢谢。 T_T
02-13 04:57:08.929 25243 25376 I python : Traceback (most recent call last):
02-13 04:57:08.930 25243 25376 I python : File "/home/dex/Desktop/avac-app/.buildozer/android/app/main.py", line 1, in <module>
02-13 04:57:08.931 25243 25376 I python : File "/home/dex/Desktop/avac-app/.buildozer/android/platform/build/build/python-installs/avacremote/kivy/base.py", line 27, in <module>
02-13 04:57:08.931 25243 25376 I python : File "/home/dex/Desktop/avac-app/.buildozer/android/platform/build/build/python-installs/avacremote/kivy/event.py", line 8, in <module>
02-13 04:57:08.932 25243 25376 I python : File "kivy/_event.pyx", line 891, in init kivy._event (kivy/_event.c:14871)
02-13 04:57:08.933 25243 25376 I python : TypeError: descriptor 'property' requires a 'kivy._event.EventDispatcher' object but received a 'method_descriptor'
这是整个日志(logcat)。 log
链接我的代码。 https://github.com/kivy/kivy/files/2856367/mycodes.zip
main.py
from kivy.base import runTouchApp
from kivy.uix.button import Label
from kivy.clock import Clock
from kivy.lang import Builder
from kivy.uix.floatlayout import FloatLayout
from kivy.uix.boxlayout import BoxLayout
from kivy.app import App
import time
import gspread
from oauth2client.service_account import ServiceAccountCredentials
from threading import Thread
print("step1 done!")
scope = ['https://www.googleapis.com/auth/drive']
credentials = ServiceAccountCredentials.from_json_keyfile_name('client_creds.json', scope)
print("step2 done!")
#authorize the account for using gspread api
client = gspread.authorize(credentials)
print("step3 done!")
# Open Client worksheet from spreadsheet with one shot
status = client.open('automated-vac-status').sheet1
print("status done")
# Open Status worksheet from spreadsheet with one shot
mode = client.open('automated-vac-mode').sheet1
print("mode done")
# Open Mode worksheet from spreadsheet with one shot
clientsheet = client.open('automated-vac-client').sheet1
print("step4 done!")
global mode_var
def getMode():
print("Getting Mode.")
currmode = mode.cell(1,1).value
currmode = int(currmode)
return currmode
def setMode(mode_val):
print("Setting Mode.")
mode.update_cell(1,1, mode_val)
mode_var = getMode()
class RootWidget(FloatLayout):
print('Root')
def toAutomatic(self):
print("toAutomatic called")
self.ids.AutoButton.text = "CHANGE TO AUTOMATIC"
self.ids.ManButton.disabled = False
self.ids.StandButton.disabled = False
self.ids.AutoButton.disabled = True
self.ids.ToggleButtonAC.disabled = True
self.ids.ToggleButtonFan.disabled = True
mode = 0
setMode(mode)
self.ids.L5.text = "AUTOMATIC MODE"
def toManual(self):
print("toManual called")
self.ids.ManButton.disabled = True
self.ids.AutoButton.disabled = False
self.ids.StandButton.disabled = False
self.ids.ToggleButtonAC.disabled = False
self.ids.ToggleButtonFan.disabled = False
mode = 1
setMode(mode)
self.ids.L5.text = "MANUAL MODE"
def toStandby(self):
print("toStandby called")
self.ids.ManButton.disabled = False
self.ids.AutoButton.disabled = False
self.ids.StandButton.disabled = True
self.ids.ToggleButtonAC.disabled = True
self.ids.ToggleButtonFan.disabled = True
mode = 2
setMode(mode)
status.update_cell(1,5,0)
status.update_cell(1,6,0)
self.ids.ToggleButtonAC.text = "OFF"
self.ids.ToggleButtonAC.state = 'normal'
self.ids.ToggleButtonFan.text = "OFF"
self.ids.ToggleButtonFan.state = 'normal'
self.ids.L5.text = "STANDBY MODE"
def getStateAC(self):
aircon_status = status.cell(1,5).value
aircon_status = int(aircon_status)
if aircon_status == 0:
self.ids.ToggleButtonAC.text = "OFF"
return 'normal'
else:
self.ids.ToggleButtonAC.text = "ON"
return 'down'
def getStateFan(self):
fan_status = status.cell(1,6).value
fan_status = int(fan_status)
if fan_status == 0:
self.ids.ToggleButtonFan.text = "OFF"
return 'normal'
else:
self.ids.ToggleButtonFan.text = "ON"
return 'down'
def setStateAC(self):
if self.ids.ToggleButtonAC.state == 'normal':
self.ids.ToggleButtonAC.text = "OFF"
status.update_cell(1,5, 0)
elif self.ids.ToggleButtonAC.state == 'down':
self.ids.ToggleButtonAC.text = "ON"
status.update_cell(1,5, 1)
def setStateFan(self):
if self.ids.ToggleButtonFan.state == 'normal':
self.ids.ToggleButtonFan.text = "OFF"
status.update_cell(1,6, 0)
elif self.ids.ToggleButtonFan.state == 'down':
self.ids.ToggleButtonFan.text = "ON"
status.update_cell(1,6, 1)
def ConditionAC(self):
aircon = status.cell(1,5).value
aircon = int(aircon)
if aircon == 0:
return 'OFF'
else:
return 'ON'
def ConditionFan(self):
fan = status.cell(1,6).value
fan = int(fan)
if fan == 0:
return 'OFF'
else:
return 'ON'
def getTemperature(self):
mode = getMode()
print(mode)
if mode == 0:
prevmode = mode
self.toAutomatic()
elif mode == 1:
prevmode = mode
self.toManual()
elif mode == 2:
prevmode = mode
self.toStandby()
Thread(target=self.autoMode).start()
temp = status.cell(1,1).value
return ''+temp+' C'
def getHumidity(self):
temp = status.cell(1,2).value
return ''+temp+'%'
def autoMode(self):
prevmode = 0
while True:
mode = getMode()
print(mode)
if prevmode != mode:
if mode == 0:
prevmode = mode
self.toAutomatic()
elif mode == 1:
prevmode = mode
self.toManual()
elif mode == 2:
prevmode = mode
self.toStandby()
#fetch data
temperature = status.cell(1,1).value
humidity = status.cell(1,2).value
aircon = status.cell(1,5).value
fan = status.cell(1,6).value
#something data
temperature = float(temperature)
temperature = "{0:.2f}".format(temperature)
humidity = float(humidity)
humidity = "{0:.2f}".format(humidity)
aircon = int(aircon)
fan = int(fan)
#tailor data
temperature = ''+temperature+' C'
humidity = ''+humidity+' %'
#update views
self.ids.LabelTempValue.text = temperature
self.ids.LabelHumValues.text = humidity
if aircon == 0:
self.ids.ToggleButtonAC.text = "OFF"
self.ids.ToggleButtonAC.state = 'normal'
else:
self.ids.ToggleButtonAC.text = "ON"
self.ids.ToggleButtonAC.state = 'down'
if fan == 0:
self.ids.ToggleButtonFan.text = "OFF"
self.ids.ToggleButtonFan.state = 'normal'
else:
self.ids.ToggleButtonFan.text = "ON"
self.ids.ToggleButtonFan.state = 'down'
print("ended update")
time.sleep(3)
return
class MainApp(App):
def build(self):
return RootWidget()
if '__main__' == __name__:
MainApp().run()
main.kv
<RootWidget>:
# this is the rule for your root widget, defining it's look and feel.
GridLayout:
cols: 2
padding: [80,20]
spacing: [80,20]
Label:
text: 'Air Conditioner'
id: L1
ToggleButton:
state: root.getStateAC()
id: ToggleButtonAC
background_color: [1,1,1,1]
on_press: root.setStateAC()
disabled: False
Label:
id: L2
text: 'Fan'
ToggleButton:
state: root.getStateFan()
id: ToggleButtonFan
background_color: [1,1,1,1]
on_press: root.setStateFan()
disabled: False
Label:
id: LabelTemp
text: 'Temperature:'
Label:
id: LabelTempValue
text: root.getTemperature()
background_color: [1,1,1,1]
Label:
id: LabelHum
text: 'Humidity:'
Label:
id: LabelHumValues
text: root.getHumidity()
background_color: [1,1,1,1]
Button:
id: StandButton
on_press: root.toStandby()
text: 'CHANGE TO STANDBY'
background_color: [1,3,.9,9]
disabled: False
Button:
id: AutoButton
on_press: root.toAutomatic()
text: 'CHANGE TO AUTOMATIC'
background_color: [2,2,.8,1]
disabled: False
Button:
id: ManButton
on_press: root.toManual()
text: 'CHANGE TO MANUAL'
background_color: [2,1,.8,1]
disabled: False
Label:
id: L5
text: ""