Kivy - фоновое приложение не работает должным образом после выключения экрана

Я создал приложение для устройств Android, чтобы считывать данные датчиков (акселерометр, компас и гироскоп) как можно быстрее.

Тем не менее, он уже работает как фоновое приложение, так что я могу выйти из приложения, и он все еще читает датчики. Когда экран отключается (по времени или вручную), приложение перестает сохранять считанные данные датчика.

Если вы можете помочь мне в любом случае, я был бы очень признателен.

Вот мой код -> main.py:

from kivy.app import App
from kivy.lang import Builder    
from kivy.uix.boxlayout import BoxLayout
from kivy.uix.popup import Popup
from kivy.uix.label import Label
from kivy.uix.button import Button

from android import AndroidService

import atexit

kv = '''
BoxLayout:
    canvas.before:
        Color:
            rgba: 1, 1, 1, 1
        Rectangle:           
            pos: self.pos
            size: self.size
            source: 'Pictures/background_3.jpeg'
    orientation: 'vertical' 

    Label:  
        id: time_label          

    Label:
        id: label
        font_size: self.width/24
        text: ' '

    BoxLayout:
        orientation: 'vertical'
#        spacing: '30dp'
        Button:
            font_size: self.height/2
            id: toggle_button
            text: 'Start'
            on_press: app.start_measuring() 
            background_color: (0.1,0.2,0.79,1)       
        Button:
            font_size: self.height/2
            id: toggle_button
            text: 'Stop'
            on_press: app.stop_measuring() 
            background_color: (0.1,0.2,0.79,1)     
        Button:
            id: clear_button
            font_size: self.height/2
            text: 'Delete Data'
            on_press: app.ask_for_deletion()
            background_color: (0.8,0.1,0.1,1)            
'''

def exit_handler():
    if not out_file.closed:
        out_file.close()  

class AirApp(App):
    def build(self): 
        self.service = None                  
        self.root = Builder.load_string(kv)
        return self.root

    def start_measuring(self):                    
        self.root.ids.label.text = "Measuring ..." 
        service = AndroidService('AirApp', 'measuring')
        service.start('service started')
        self.service = service                      

    def stop_measuring(self):        
        self.root.ids.label.text = "Measurement stopped"
        if self.service: 
            self.service.stop()
            self.service = None

    def do_deletion(self,event):          #deletes file
        self.root.ids.label.text = "Measured data deleted"
        self.popup.dismiss()
        if self.service: 
            self.service.stop()
            self.service = None
        out_file = open("/sdcard/sensor_data.txt", "r+")
        out_file.truncate()
        out_file.close()       

    def ask_for_deletion(self):          #popup asking for intention 
        box = BoxLayout(orientation='vertical')
        content_cancel = Button(text='No', font_size = self.root.width/18)
        content_accept = Button(text='Yes', font_size = self.root.width/18)
        box.add_widget(Label(text='Are you sure that you want\nto delete all data irrevocably?', font_size = self.root.width/18))
        box.add_widget(content_cancel)
        box.add_widget(content_accept)
        self.popup = Popup(title='Delete data?', title_size = self.root.width/14, 
                      size_hint=(None, None), size=(self.root.width*3/4, self.root.height*6/7),
                      content=box)                     
        content_cancel.bind(on_release=self.popup.dismiss)
        content_accept.bind(on_release=self.do_deletion)                       
        self.popup.open()

    def on_pause(self):
        return True

    def on_resume(self):
        pass      

if __name__ == '__main__':    
    out_file = open("/sdcard/sensor_data.txt","a")
    out_file.close()
    atexit.register(exit_handler)       #if app gets forced to close: close file 
    AirApp().run()

А здесь в служебной папке находится другой (фоновый скрипт) main.py:

from plyer import accelerometer
from plyer import compass
from plyer import gyroscope
from plyer import gps

import atexit
import time

def exit_handler():
    accelerometer.disable()
    compass.disable()
    gyroscope.disable() 
    try:
        gps.stop()
    except NotImplementedError:
        import traceback
        traceback.print_exc()

def measure():
    out_file = open("/sdcard/sensor_data.txt","a")
    val_acceleration = accelerometer.acceleration
    val_compass = compass.orientation
    val_gyroscope = gyroscope.orientation
    try:
        safe_string = "Ax " + str(val_acceleration[0]) + "\n" + "Ay " + str(val_acceleration[1]) + "\n" + "Az " + str(val_acceleration[2]) + "\n"            
    except:
        safe_string = 'Ax 0.0\nAy 0.0\nAz 0.0\n'        
    out_file.write(safe_string)        

    try:
        safe_string = "Cx " + str(val_compass[0]) + "\n" + "Cy " + str(val_compass[1]) + "\n" + "Cz " + str(val_compass[2]) + "\n"            
    except:
        safe_string = 'Cx 0.0\nCy 0.0\nCz 0.0\n'
    out_file.write(safe_string)

    try:
        safe_string = "Gyx " + str(val_gyroscope[0]) + "\n" + "Gyy " + str(val_gyroscope[1]) + "\n" + "Gyz " + str(val_gyroscope[2]) + "\n"            
    except:
        safe_string = 'Gyx 0.0\nGyy 0.0\nGyz 0.0\n'            
    out_file.write(safe_string)    
    out_file.write("T1 " + str(long(time.time()*10**6)) + 'e-6\n\n')    # in seconds; for evaluation: *10**(-6)
    out_file.close()

if __name__ == '__main__':   
    accelerometer.enable()
    compass.enable()
    gyroscope.enable()  
    atexit.register(exit_handler)       #if app gets forced to close: close file  
    while True:
        measure()    

    accelerometer.disable()
    compass.disable()
    gyroscope.disable() 

1 ответ

используйте службу kivy, чтобы запустить операцию в фоновом режиме

https://blog.kivy.org/2014/01/building-a-background-application-on-android-with-kivy/

Другие вопросы по тегам