Slide.py :  » Game-2D-3D » Pyzzle » pyzzle-0.9 » pyzzle » Python Open Source

Home
Python Open Source
1.3.1.2 Python
2.Ajax
3.Aspect Oriented
4.Blog
5.Build
6.Business Application
7.Chart Report
8.Content Management Systems
9.Cryptographic
10.Database
11.Development
12.Editor
13.Email
14.ERP
15.Game 2D 3D
16.GIS
17.GUI
18.IDE
19.Installer
20.IRC
21.Issue Tracker
22.Language Interface
23.Log
24.Math
25.Media Sound Audio
26.Mobile
27.Network
28.Parser
29.PDF
30.Project Management
31.RSS
32.Search
33.Security
34.Template Engines
35.Test
36.UML
37.USB Serial
38.Web Frameworks
39.Web Server
40.Web Services
41.Web Unit
42.Wiki
43.Windows
44.XML
Python Open Source » Game 2D 3D » Pyzzle 
Pyzzle » pyzzle 0.9 » pyzzle » Slide.py
"""
The basic building blocks of myst games.
"""
import pygame, os
from pygame.sprite import Group
from pygame.rect import Rect
from pygame.surface import Surface
from RelativeRect import RelativeRect
from Hotspot import Hotspot
from Panel import Panel
from DB import Table
import pyzzle
import standard
import Text
import media

class Slide(Panel):
    """The basic building blocks of myst games.
    A typical slide represents a location the player can visit in the game world.
    Some slides may also represent items or switches that the player can interact with.  
    
    Every Slide has its own image file in the game world. 
    When the player encounters the Slide, he is presented with this image. 
    The player clicks on parts of the slide in order to perform certain actions.
    These parts of the slide are called Hotspots.
    
    As a subclass of Panel, the Slide class resembles both the Sprite and Group 
    classes of Pygame. As Sprites, they can blit an image to the screen, but as
    Groups, they can manage the behavior of other Sprites that are nested within them.
    Typically, Hotspots are the only Sprites nested within Slides, but it is possible
    to store other types of Sprites, such as Text, Movies, and even other Slides."""
    
    __metaclass__=Table
    
    
    @staticmethod
    def _load(row):
        stage=pyzzle.stages[row.stage] if row.stage else None
        slide=Slide(row.id, row.image, stage, ambiencefile=row.ambientSound, 
                    layer=row.layer, dialog=row.dialog)
        slide.rectRel=RelativeRect((row.rectleft, row.recttop, row.rectheight, row.rectwidth))
        slide._refs={}
        slide._movementSoundfile=row.movementSound
        if stage and stage.movementSound and not row.movementSound:
            slide._movementSoundfile=stage.movementSound
        for ref in 'forward', 'up', 'down', 'right', 'left':
            slide._refs[ref]=row[ref]
        return slide
    def _loadRefs(self):
        rectRels=\
        {'left':    (0,0,.2,1.),
         'right':   (.8,0,.2,1.),
         'forward': (.2,.2,.6,.6),
         'up':      (0,0,1.,.2),
         'down':    (0,.8,1.,.2)
         }
        transitions=\
        {'left':    standard.scrollLeft,
         'right':   standard.scrollRight,
         'forward': standard.transition,
         'up':      standard.scrollUp,
         'down':    standard.scrollDown
         }
        for ref in self._refs.keys():
            if pyzzle.design or self._refs[ref] in Slide:
                link=Slide[self._refs[ref]] if self._refs[ref] in Slide else None
                hotspot=Hotspot(self, link, id=ref, 
                                rectRel=RelativeRect(rectRels[ref]), 
                                cursor=ref+'.png', onTransition=transitions[ref],
                                layer=-1., _template=True)
                setattr(self, ref, hotspot)
                self.add(hotspot)
        if self.forward:
            self.forward.cursor='fwd.png'
            self.forward.soundfile = self._movementSoundfile
        if self.left and self.right and self.left.link == self.right.link:
            self.right.cursor='right180.png'
            self.left.cursor='left180.png'
        
    def __init__(self, id, file, stage=None, parent=None,
                 ambiencefile=None, rectRel=None, layer=0, 
                 cursor='', dialog=None):
        """Creates a slide. 
        @param id: A unique identifier for the Slide. Used to refer to the Slide 
            in scripts and the database
        @param file: The name of the image file drawn by the slide. 
        @type stage: Stage
        @param stage: An area of the game in which the slide occurs. Used to determine
            default ambience and movement sounds.
        @type parent: Panel
        @param parent: The panel that the slide is nested within. 
            The default is pyzzle.panel.
            Note: This will not add the slide to the panel. You still need to add it
            using Slide.enter() or one of the transition functions
        @param ambiencefile: The name of the sound file that is played in a loop when
            the player reaches the slide.
        @type rectRel: RelativeRect
        @param rectRel: The rectangle occupied by the Slide.
            Currently, rect width and height do not resize the slide image.
        @type layer: float
        @param layer: The layer of the Slide. Larger numbers represent upper layers. 
            When the player clicks on an area of the Slide where two Sprites overlap,
            the sprite with the topmost layer is the only one that's activated.
        @param cursor: The name of the cursor file that is displayed when no hotspots are
            highlighted. The default is defined by Panel.cursorDefault. None displays no cursor.
        @param dialog: The name of the sound file that is played when the player reaches
            the slide for the first time. This was added specifically for the "Dryzzle" 
            video game, and may be dropped in a future version.
        """
        if id: Slide[id]=self
        if not parent: parent=pyzzle.panel
        Panel.__init__(self)
        self.id = id
        self.stage=stage
        self._file = file
        self._ambiencefile=ambiencefile
        self._movementSoundfile=None
        self._layer=layer
        self.rectRel=rectRel
        self.cursor=Panel.cursorDefault if cursor =='' else cursor
        self.dialog=dialog
        
        self.parent=parent
        self._rect=None
        self.loaded=False
        """Whether the player has loaded the slide's image file 
        in the current game session."""
        self.links=Group()
        """All Hotspots that link to this slide when clicked."""
        self.visited=False
        """Whether the player has previously visited the slide."""
        
        for ref in 'forward', 'up', 'down', 'right', 'left':
            setattr(self, ref, None)
        
    
    def _loadImage(self, image):
        self.loaded=True
        screen=pyzzle.screen.get_rect()
        rect=image.get_rect()
        rect.center=self.parent.rect.center
        if self.rectRel:
            rectAbs=self.rectRel.absolute(self.parent.rect)
            for attr in 'left','top','width','height':
                value=getattr(rectAbs, attr)
                if value:   setattr(rect,attr,value)
            
        if rect.width > screen.width:
            panHotspot=Hotspot(self, None, cursor='left.png',
                             onHighlight=standard.panLeft, 
                             onTransition=lambda *p,**k:None, 
                             layer=.1, _template=True)
            panWidth=.2
            panHotspot.rect=Rect(0, rect.top,
                                 screen.width*panWidth,
                                 rect.height)
            self.add(panHotspot)
            panHotspot=Hotspot(self, None, cursor='right.png',
                             onHighlight=standard.panRight, 
                             onTransition=lambda *p,**k:None, 
                             layer=.1, _template=True)
            panHotspot.rect=Rect(screen.width*(1-panWidth),
                                 rect.top,
                                 screen.width*(panWidth),
                                 rect.height)
            self.add(panHotspot)
        self._rect=rect
    def _getImage(self):
        """The image displayed by the Slide."""
        file=self.file
        if self.stage:
            file=os.path.join(self.stage.folder, file)
        image=media.images.load(file)
        if not self.loaded: self._loadImage(image)
        return image
    image=property(_getImage)
    
    def _getRect(self):
        """The portion of the screen occupied by the slide.
        rect coordinates are determined by rectRel. 
        If a coordinate in rectRel is None, the coordinate is 
        determined by the slide's image size. 
        """
        self._getImage()
        return self._rect
    rect=property(_getRect)

    
    def _setFile(self, file):
        self._file=file
        self.loaded=False
    def _getFile(self):
        """The name of the image file displayed by the Slide.
        Resets self.loaded to False"""
        return self._file
    file=property(_getFile, _setFile)

        
    def _getAmbiencefile(self):
        """The name of the sound file that is played in a loop when
        the player reaches the slide. If none is specified, it returns 
        the default for the slide's stage."""
        if self._ambiencefile:
            return self._ambiencefile
        if self.stage:
            return self.stage.ambientSound
    def _setAmbiencefile(self,value):
        self._ambiencefile=value
    ambiencefile=property(_getAmbiencefile, _setAmbiencefile)
    
    def draw(self, screen):
        """Draws the slide's image to screen, 
        then draws any sprites within the Slide."""
        screen.blit(self.image, self._rect)
        Panel.draw(self, screen)
        
        if pyzzle.design:
            Text.Text(self.id).draw(screen)
    def enter(self, oldslide=None, delay=.1):
        """Called when the user enters the Slide.
        @type oldslide: Panel
        @param oldslide: The Panel that was previously presented to the user,
            to be replaced by self
        @param delay: The time it should take for oldslide to transition to self
        """
        Panel.enter(self, oldslide, delay)
        if self.dialog and not self.visited:
            self.visited=True
            media.voices.load(self.dialog).play()
        if self.ambiencefile:
            ambience=media.sounds.load(self.ambiencefile)
            if ambience.get_num_channels() == 0:
                ambience.play(-1, fade_ms=int(delay*1000))
    def exit(self, newslide=None, delay=.1):
        """Called when the user exits the Slide.
        @type oldslide: Panel
        @param oldslide: The Panel that was previously presented to the user,
            to be replaced by self
        @param delay: The time it should take for oldslide to transition to self,
            in seconds
        """
        Panel.exit(self, newslide, delay)
        if self.ambiencefile and \
           ((not hasattr(newslide, 'ambiencefile')) or self.ambiencefile!=newslide.ambiencefile):
            ambience=media.sounds.load(self.ambiencefile)
            ambience.fadeout(int(delay*1000))
            
            
    def _cells(self):
        cells=  \
        {'id':self.id,
         'stage':self.stage.id if self.stage else None,
         'image':self.file,
         'ambientSound' :self._ambiencefile,
         'movementSound':self._movementSoundfile,
         'left'     :self.left.link.id if self.left and self.left.link else None,
         'right'    :self.right.id if self.left else None,
         'up'       :self.up.id if self.left else None,
         'down'     :self.down.id if self.left else None,
         'forward'  :self.forward.id if self.left else None,
         'layer'    :self._layer,
         'dialog'   :self.dialog}
        if self.rectRel:
            left,top,width,height=self.rectRel
            cells['rectleft']   =left
            cells['recttop']    =top
            cells['rectwidth']  =width
            cells['rectheight'] =height
        for ref in 'forward', 'up', 'down', 'right', 'left':
            hotspot=getattr(self,ref)
            if hotspot and hotspot.link:
                cells[ref]=hotspot.link.id
        return cells
    def insert(self):
        """Inserts a representation of the slide into the database."""
        pyzzle.datafile.insert('Slide',self._cells())
    def delete(self):
        """Deletes the slide's representation in the database."""
        pyzzle.datafile.delete('Slide',self.id)
    def update(self):   
        """Updates the slide's representation in the database.
        @note: While this overrides Sprite.update(), it does not perform 
            the same behavior!
        """
        pyzzle.datafile.update('Slide',self._cells())
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.