diff src/parpg/application.py @ 0:1fd2201f5c36

Initial commit of parpg-core.
author M. George Hansen <technopolitica@gmail.com>
date Sat, 14 May 2011 01:12:35 -0700
parents
children d60f1dab8469
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/parpg/application.py	Sat May 14 01:12:35 2011 -0700
@@ -0,0 +1,230 @@
+#   This program is free software: you can redistribute it and/or modify
+#   it under the terms of the GNU General Public License as published by
+#   the Free Software Foundation, either version 3 of the License, or
+#   (at your option) any later version.
+
+#   This program is distributed in the hope that it will be useful,
+#   but WITHOUT ANY WARRANTY; without even the implied warranty of
+#   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+#   GNU General Public License for more details.
+
+#   You should have received a copy of the GNU General Public License
+#   along with this program.  If not, see <http://www.gnu.org/licenses/>.
+"""This module contains the main Application class 
+and the basic Listener for PARPG """
+
+import os
+import sys
+
+from fife import fife
+from fife.extensions import pychan
+from fife.extensions.serializers.xmlanimation import XMLAnimationLoader
+from fife.extensions.basicapplication import ApplicationBase
+
+from parpg import console
+from parpg.font import PARPGFont
+from parpg.gamemodel import GameModel
+from parpg.mainmenuview import MainMenuView
+from parpg.mainmenucontroller import MainMenuController
+from parpg.common.listeners.event_listener import EventListener
+from parpg.common.listeners.key_listener import KeyListener
+from parpg.common.listeners.mouse_listener import MouseListener
+from parpg.common.listeners.command_listener import CommandListener
+from parpg.common.listeners.console_executor import ConsoleExecuter
+from parpg.common.listeners.widget_listener import WidgetListener
+
+class KeyFilter(fife.IKeyFilter):
+    """
+    This is the implementation of the fife.IKeyFilter class.
+    
+    Prevents any filtered keys from being consumed by guichan.
+    """
+    def __init__(self, keys):
+        fife.IKeyFilter.__init__(self)
+        self._keys = keys
+
+    def isFiltered(self, event):
+        """Checks if an key is filtered"""
+        return event.getKey().getValue() in self._keys
+
+class ApplicationListener(KeyListener,
+                        MouseListener,
+                        ConsoleExecuter,
+                        CommandListener,
+                        WidgetListener):    
+    """Basic listener for PARPG"""
+        
+    def __init__(self, event_listener, engine, view, model):
+        """Initialize the instance.
+           @type engine: fife.engine
+           @param engine: ???
+           @type view: viewbase.ViewBase
+           @param view: View that draws the current state
+           @type model: GameModel
+           @param model: The game model"""
+
+        KeyListener.__init__(self, event_listener)
+        MouseListener.__init__(self, event_listener)
+        ConsoleExecuter.__init__(self, event_listener)
+        CommandListener.__init__(self, event_listener)
+        WidgetListener.__init__(self, event_listener)        
+        self.engine = engine
+        self.view = view
+        self.model = model
+        keyfilter = KeyFilter([fife.Key.ESCAPE])
+        keyfilter.__disown__()        
+        
+        engine.getEventManager().setKeyFilter(keyfilter)
+        self.quit = False
+        self.about_window = None
+        self.console = console.Console(self)
+
+    def quitGame(self):
+        """Forces a quit game on next cycle.
+           @return: None"""
+        self.quit = True
+
+    def onConsoleCommand(self, command):
+        """
+        Called on every console comand, delegates calls  to the a console
+        object, implementing the callbacks
+        @type command: string
+        @param command: the command to run
+        @return: result
+        """
+        return self.console.handleConsoleCommand(command)
+
+    def onCommand(self, command):
+        """Enables the game to be closed via the 'X' button on the window frame
+           @type command: fife.Command
+           @param command: The command to read.
+           @return: None"""
+        if(command.getCommandType() == fife.CMD_QUIT_GAME):
+            self.quit = True
+            command.consume()
+
+class PARPGApplication(ApplicationBase):
+    """Main Application class
+       We use an MVC model model
+       self.gamesceneview is our view,self.model is our model
+       self.controller is the controller"""
+       
+    def __init__(self, setting):
+        """Initialise the instance.
+           @return: None"""
+        self._setting = setting
+        self.engine = fife.Engine()
+        self.loadSettings()
+        self.engine.init()
+        self._animationloader = XMLAnimationLoader(self.engine.getImagePool(),
+                                                   self.engine.getVFS())
+        self.engine.getAnimationPool().addResourceLoader(self._animationloader)
+
+        pychan.init(self.engine, debug = True)
+        pychan.setupModalExecution(self.mainLoop,self.breakFromMainLoop)
+
+        self.quitRequested = False
+        self.breakRequested = False
+        self.returnValues = []
+        #self.engine.getModel(self)
+        self.model = GameModel(self.engine, setting)
+        self.model.readMapFiles()
+        self.model.readObjectDB()
+        self.model.getAgentImportFiles()
+        self.model.readAllAgents()
+        self.model.getDialogues()
+        self.view = MainMenuView(self.engine, self.model)
+        self.loadFonts()
+        self.event_listener = EventListener(self.engine)
+        self.controllers = []
+        controller = MainMenuController(self.engine, self.view, self.model, 
+                                        self)
+        #controller.initHud()
+        self.controllers.append(controller)
+        self.listener = ApplicationListener(self.event_listener,
+                                            self.engine, 
+                                            self.view, 
+                                            self.model)
+        #start_map = self._setting.fife.get("PARPG", "Map")
+        #self.model.changeMap(start_map)
+
+    def loadFonts(self):
+        # add the fonts path to the system path to import font definitons
+        sys.path.insert(0, os.path.join(self._setting.system_path, 
+                                        self._setting.fife.FontsPath))
+        from oldtypewriter import fontdefs
+
+        for fontdef in fontdefs:
+            pychan.internal.get_manager().addFont(PARPGFont(fontdef,
+                                                            self._setting))
+                
+
+    def loadSettings(self):
+        """
+        Load the settings from a python file and load them into the engine.
+        Called in the ApplicationBase constructor.
+        """
+
+        engineSetting = self.engine.getSettings()
+        engineSetting.setDefaultFontGlyphs(self._setting.fife.FontGlyphs)
+        engineSetting.setDefaultFontPath(os.path.join(self._setting.system_path,
+                                                   self._setting.fife.FontsPath,
+                                                   self._setting.fife.Font))
+        engineSetting.setDefaultFontSize(self._setting.fife.DefaultFontSize)
+        engineSetting.setBitsPerPixel(self._setting.fife.BitsPerPixel)
+        engineSetting.setInitialVolume(self._setting.fife.InitialVolume)
+        engineSetting.setSDLRemoveFakeAlpha(self._setting.fife.SDLRemoveFakeAlpha)
+        engineSetting.setScreenWidth(self._setting.fife.ScreenWidth)
+        engineSetting.setScreenHeight(self._setting.fife.ScreenHeight)
+        engineSetting.setRenderBackend(self._setting.fife.RenderBackend)
+        engineSetting.setFullScreen(self._setting.fife.FullScreen)
+        engineSetting.setVideoDriver(self._setting.fife.VideoDriver)
+        engineSetting.setLightingModel(self._setting.fife.Lighting)
+        engineSetting.setColorKeyEnabled(self._setting.fife.ColorKeyEnabled)
+
+        engineSetting.setColorKey(*[int(digit) 
+                                    for digit in self._setting.fife.ColorKey])
+
+        engineSetting.setWindowTitle(self._setting.fife.WindowTitle)
+        engineSetting.setWindowIcon(os.path.join(self._setting.system_path, 
+                                                 self._setting.fife.IconsPath,
+                                                 self._setting.fife.WindowIcon))
+
+    def createListener(self):
+        """ __init__ takes care of creating an event listener, so
+            basicapplication's createListener is harmful. Without 
+            overriding it, the program quit's on esc press, rather than
+            invoking the main menu
+        """
+        pass
+
+    def pushController(self, controller):
+        """Adds a controller to the list to be the current active one."""
+        self.controllers[-1].pause(True)
+        self.controllers.append(controller)
+    
+    def popController(self):
+        """Removes and returns the current active controller, unless its the last one"""
+        ret_controller = None
+        if self.controllers.count > 1:
+            ret_controller = self.controllers.pop()
+            self.controllers[-1].pause(False)
+        ret_controller.onStop()
+        return ret_controller
+    
+    def switchController(self, controller):
+        """Clears the controller list and adds a controller to be the current active one"""
+        for old_controller in self.controllers:
+            old_controller.onStop()
+        self.controllers = []
+        self.controllers.append(controller)
+    
+    def _pump(self):
+        """Main game loop.
+           There are in fact 2 main loops, this one and the one in GameSceneView.
+           @return: None"""
+        if self.listener.quit:
+            self.breakRequested = True #pylint: disable-msg=C0103
+        else:
+            for controller in self.controllers:
+                controller.pump()