2019-12-02 08:45:03 -05:00
#!/bin/python
# -*- coding: utf-8 -*-
""" Standard initializations and functions shared by all games. """
import configparser
import os
from os import listdir
from os . path import isfile , join
from inspect import isfunction
from xdg import BaseDirectory
import pygame
import pyperclip
import random
2019-12-04 13:39:16 -05:00
import re
2019-12-02 08:45:03 -05:00
import requests
2019-12-08 08:08:20 -05:00
import webbrowser
2019-12-05 10:56:58 -05:00
# Global variable for speech provider
try :
import speechd
spd = speechd . Client ( )
speechProvider = " speechd "
2019-12-06 18:20:45 -05:00
except ImportError :
import accessible_output2 . outputs . auto
s = accessible_output2 . outputs . auto . Auto ( )
speechProvider = " accessible_output2 "
except ImportError :
print ( " No other speech providers found. " )
exit ( )
2019-12-02 08:45:03 -05:00
import subprocess
import time
localConfig = configparser . ConfigParser ( )
globalConfig = configparser . ConfigParser ( )
def write_config ( writeGlobal = False ) :
if writeGlobal == False :
with open ( gamePath , ' w ' ) as configfile :
localConfig . write ( configfile )
else :
with open ( globalPath , ' w ' ) as configfile :
globalConfig . write ( configfile )
def read_config ( section , value , readGlobal = False ) :
if readGlobal == False :
with open ( gamePath , ' r ' ) as configfile :
return localConfig . read ( section , value )
else :
return globalConfig . read ( section , value )
def speak ( text , interupt = True ) :
2019-12-05 10:56:58 -05:00
if speechProvider == " speechd " :
if interupt == True : spd . cancel ( )
spd . say ( text )
2019-12-06 18:20:45 -05:00
else :
if speechProvider == " accessible_output2 " :
s . speak ( text , interrupt = True )
2019-12-02 08:45:03 -05:00
def exit_game ( ) :
2019-12-06 18:20:45 -05:00
if speechProvider == " speechd " : spd . close ( )
2019-12-02 08:45:03 -05:00
pygame . mixer . music . stop ( )
pygame . quit ( )
exit ( )
def initialize_gui ( gameTitle ) :
# Check for, and possibly create, storm-games path
global globalPath
global gamePath
globalPath = BaseDirectory . xdg_config_home + " /storm-games "
gamePath = globalPath + " / " + str . lower ( str . replace ( gameTitle , " " , " - " ) + " config " )
globalPath = globalPath + " /config "
if not os . path . exists ( gamePath ) : os . makedirs ( gamePath )
# Seed the random generator to the clock
random . seed ( )
# Set game's name
global gameName
gameName = gameTitle
# start pygame
pygame . init ( )
# start the display (required by the event loop)
pygame . display . set_mode ( ( 320 , 200 ) )
pygame . display . set_caption ( gameTitle )
2019-12-05 12:33:54 -05:00
# Set 32 channels for sound by default
pygame . mixer . init ( )
pygame . mixer . set_num_channels ( 32 )
2019-12-05 10:30:44 -05:00
# Reserve the cut scene channel
pygame . mixer . set_reserved ( 0 )
2019-12-02 08:45:03 -05:00
# Load sounds from the sound directory and creates a list like that {'bottle': 'bottle.ogg'}
soundFiles = [ f for f in listdir ( " sounds/ " ) if isfile ( join ( " sounds/ " , f ) ) and ( f . split ( ' . ' ) [ 1 ] . lower ( ) in [ " ogg " , " wav " ] ) ]
#lets make a dict with pygame.mixer.Sound() objects {'bottle':<soundobject>}
soundData = { }
for f in soundFiles :
soundData [ f . split ( ' . ' ) [ 0 ] ] = pygame . mixer . Sound ( " sounds/ " + f )
soundData [ ' game-intro ' ] . play ( )
time . sleep ( soundData [ ' game-intro ' ] . get_length ( ) )
return soundData
2019-12-05 10:30:44 -05:00
def cut_scene ( sounds , soundName ) :
pygame . event . clear ( )
pygame . mixer . stop ( )
c = pygame . mixer . Channel ( 0 )
c . play ( sounds [ soundName ] )
while pygame . mixer . get_busy ( ) :
2019-12-05 12:33:54 -05:00
event = pygame . event . poll ( )
2019-12-06 09:40:36 -05:00
if event . type == pygame . KEYDOWN and event . key in [ pygame . K_ESCAPE , pygame . K_RETURN , pygame . K_SPACE ] :
2019-12-05 10:30:44 -05:00
pygame . mixer . stop ( )
pygame . event . pump ( )
2019-12-05 12:33:54 -05:00
def play_random ( sounds , soundName , pause = False , interrupt = False ) :
2019-12-04 18:06:03 -05:00
key = [ ]
for i in sounds . keys ( ) :
if re . match ( " ^ " + soundName + " .* " , i ) :
key . append ( i )
randomKey = random . choice ( key )
2019-12-05 12:33:54 -05:00
if interrupt == False :
sounds [ randomKey ] . play ( )
else :
cut_scene ( sounds , randomKey )
# Cut scenes override the pause option
return
2019-12-04 18:06:03 -05:00
if pause == True :
time . sleep ( sounds [ randomKey ] . get_length ( ) )
2019-12-04 13:39:16 -05:00
2019-12-02 08:45:03 -05:00
def instructions ( ) :
# Read in the instructions file
try :
with open ( ' files/instructions.txt ' , ' r ' ) as f :
info = f . readlines ( )
except :
info = [ " Instructions file is missing. " ]
display_text ( info )
def credits ( ) :
info = [
gameName + " : brought to you by Storm Dragon " , \
" Billy Wolfe, designer and coder. " , \
" https://social.wolfe.casa/storm " ]
display_text ( info )
def display_text ( text ) :
i = 0
text . insert ( 0 , " Press space to read the whole text. Use up and down arrows to navigate the text line by line. Press c to copy the current line to the clipboard or t to copy the entire text. Press enter or escape when you are done reading. " )
text . append ( " End of text. " )
speak ( text [ i ] )
while True :
event = pygame . event . wait ( )
if event . type == pygame . KEYDOWN :
if event . key == pygame . K_ESCAPE or event . key == pygame . K_RETURN : return
if event . key == pygame . K_DOWN and i < len ( text ) - 1 : i = i + 1
if event . key == pygame . K_UP and i > 0 : i = i - 1
if event . key == pygame . K_SPACE :
2019-12-05 10:30:44 -05:00
speak ( ' ' . join ( text [ 1 : ] ) )
2019-12-02 08:45:03 -05:00
else :
speak ( text [ i ] )
if event . key == pygame . K_c :
try :
pyperclip . copy ( text [ i ] )
speak ( " Copied " + text [ i ] + " to the clipboard. " )
except :
speak ( " Failed to copy the text to the clipboard. " )
if event . key == pygame . K_t :
try :
pyperclip . copy ( ' ' . join ( text [ 1 : - 1 ] ) )
speak ( " Copied entire message to the clipboard. " )
except :
speak ( " Failed to copy the text to the clipboard. " )
event = pygame . event . clear ( )
time . sleep ( 0.001 )
def learn_sounds ( sounds ) :
loop = True
pygame . mixer . music . pause ( )
i = 0
soundFiles = [ f for f in listdir ( " sounds/ " ) if isfile ( join ( " sounds/ " , f ) ) and ( f . split ( ' . ' ) [ 1 ] . lower ( ) in [ " ogg " , " wav " ] ) and ( f . split ( ' . ' ) [ 0 ] . lower ( ) not in [ " game-intro " , " music_menu " ] ) ]
# j keeps track of last spoken index so it isn't voiced on key up.
j = - 1
while loop == True :
if i != j :
speak ( soundFiles [ i ] [ : - 4 ] )
j = i
event = pygame . event . wait ( )
if event . type == pygame . KEYDOWN :
if event . key == pygame . K_ESCAPE : return " menu "
if event . key == pygame . K_DOWN and i < len ( soundFiles ) - 1 :
i = i + 1
if event . key == pygame . K_UP and i > 0 :
i = i - 1
if event . key == pygame . K_RETURN :
try :
soundName = soundFiles [ i ] [ : - 4 ]
sounds [ soundName ] . play ( )
continue
except :
j = - 1
speak ( " Could not play sound. " )
continue
event = pygame . event . clear ( )
time . sleep ( 0.001 )
def game_menu ( * options ) :
loop = True
if pygame . mixer . music . get_busy ( ) :
pygame . mixer . music . unpause ( )
else :
pygame . mixer . music . load ( " sounds/music_menu.ogg " )
pygame . mixer . music . set_volume ( 0.75 )
pygame . mixer . music . play ( - 1 )
i = 0
# j keeps track of last spoken index so it isn't voiced on key up.
j = - 1
while loop == True :
if i != j :
speak ( options [ i ] )
j = i
event = pygame . event . wait ( )
if event . type == pygame . KEYDOWN :
if event . key == pygame . K_ESCAPE : exit_game ( )
if event . key == pygame . K_DOWN and i < len ( options ) - 1 :
i = i + 1
if options [ i ] != " donate " : pygame . mixer . music . unpause ( )
if event . key == pygame . K_UP and i > 0 :
i = i - 1
if options [ i ] != " donate " : pygame . mixer . music . unpause ( )
if event . key == pygame . K_RETURN :
try :
j = - 1
eval ( options [ i ] + " () " )
continue
except :
j = - 1
return options [ i ]
continue
event = pygame . event . clear ( )
time . sleep ( 0.001 )
def donate ( ) :
pygame . mixer . music . pause ( )
2019-12-08 15:50:30 -05:00
webbrowser . open ( ' https://www.paypal.me/billywolfe/ ' )