2016-01-21 123 views
0

我希望將kivy應用程序的功能作爲其他kivy應用程序的啓動程序,具體取決於輸入。我在下面實現它的方式顯然不起作用(因爲kv文件被重新加載並重新應用它的樣式,因此增加了越來越多的按鈕),並且當我點擊Esc退出時跟蹤建議似乎也有一些遞歸。與Kivy嵌套/交互應用程序

我得到的是app1.kv然而加載多次,在文檔中的App.load_kv()警告它說

調用此方法的第一次,如果沒有 widget樹一直是應用程序正在運行爲此應用程序構建之前。

這意味着我應該可以對run()一個應用程序多次?

這裏是我的代碼:

main.py

from kivy.uix.widget import Widget 
from kivy.uix.gridlayout import GridLayout 
from kivy.app import App 
from kivy.properties import ObjectProperty 
from kivy.uix.button import Button 
from kivy.clock import Clock 
from kivy.logger import Logger 
from kivy.lang import Builder 

class OutsideApp(App): 
    current_app = ObjectProperty(None) 

    def build(self): 
     Clock.schedule_interval(self.update, 3) 
     return Widget() 

    def update(self, dt): 
     if isinstance(self.current_app, App): 
      self.current_app.stop() 
     if isinstance(self.current_app, App1): 
      self.current_app = App2() 
     else: 
      self.current_app = App1() 
     self.current_app.run() 

class App1(App): 
    pass 
class App2(App): 
    def build(self): 
     gl = Builder.load_string("<[email protected]>:\n cols: 2\n Button:\n  text: \"hello 2\"\nSequencesGame:") 
     return gl 

if __name__ == '__main__': 
    oa = OutsideApp() 
    oa.run() 

app1.kv

#:kivy 1.0.9 
<[email protected]>: 
    cols: 2 
    Button: 
     text: "hello 111" 
SequencesGame: 

這似乎是即使應用程序沒有嵌套的問題:

main2.py

from kivy.app import App 

from kivy.clock import Clock 
from kivy.logger import Logger 
from kivy.lang import Builder 

class App1(App): 
    pass 
class App2(App): 
    def build(self): 
     return Builder.load_string("<[email protected]>:\n cols: 2\n Button:\n  text: \"hello 2\"\nSequencesGame:") 

current_app = None 

def switch(*args): 
    global current_app 
    if isinstance(current_app, App): 
     current_app.stop() 
    if isinstance(current_app, App1): 
     current_app = App2() 
    else: 
     current_app = App1() 
    current_app.run() 

if __name__ == '__main__': 
    Clock.schedule_interval(switch, 2) 
    switch() 
+0

你就不能有一個應用程序與下屏幕管理多個屏幕,每個屏幕,,另一個應用程序'? – jligeza

+0

我想重複使用現有的應用程序。此外,像配置文件似乎很好地封裝在應用程序級別。 – zeeMonkeez

+1

爲什麼不在其他子程序中運行其他應用程序? – inclement

回答

0

最後,我跟着@使用multiprocessing的惡劣的建議。這是一個基本的實現(不通過通信管道或隊列):

import sys 
import multiprocessing 
from kivy.app import App 
from kivy.lang import Builder 
from time import sleep#, localtime, time 

def str_to_class(str): 
    return reduce(getattr, str.split("."), sys.modules[__name__]) 

class App1(App): 
    def build(self): 
     return Builder.load_string("BoxLayout:\n Button:\n  text: \"hello 1\"") 

class App2(App): 
    def build(self): 
     return Builder.load_string("BoxLayout:\n Button:\n  text: \"hello 2\"") 


class Wrapper(object): 
    def __init__(self, *kargs, **kwargs): 
     super(Wrapper, self).__init__() 
     self.running_app = None 
     self.next_app = 'App1' 

    def change_running_app(self, name='App1'): 
     if self.running_app is not None: 
      self.running_app.terminate() 
     self.running_app = multiprocessing.Process(target=self.run_app, kwargs={'name':name}) 
     self.running_app.start() 

    def run_app(self, name='App1'): 
     app = str_to_class(name)() 
     app.run() 

    def swap(self): 
     self.change_running_app(name=self.next_app) 
     self.next_app = ['App1', 'App2']['App1' is self.next_app] 

if __name__ == '__main__': 
    counter = 0 
    w = Wrapper() 
    while True: 
     counter += 1 
     print "Started App instance {}".format(counter) 
     w.swap() 
     sleep(5)