mirror of
https://github.com/shlomif/PySolFC.git
synced 2025-04-05 00:02:29 -04:00
* improved tile binding
git-svn-id: https://pysolfc.svn.sourceforge.net/svnroot/pysolfc/PySolFC/trunk@85 39dd0a4e-7c14-0410-91b3-c4f2d318f732
This commit is contained in:
parent
4a1892eb97
commit
4cebac735e
10 changed files with 453 additions and 115 deletions
357
data/tcl/menu8.4.tcl
Normal file
357
data/tcl/menu8.4.tcl
Normal file
|
@ -0,0 +1,357 @@
|
||||||
|
# this file from tkabber project
|
||||||
|
|
||||||
|
namespace eval :: {
|
||||||
|
|
||||||
|
proc myMenuButtonDown {args} {
|
||||||
|
global myMenuFlag myMenuMotion
|
||||||
|
eval ::tk::MenuButtonDown $args
|
||||||
|
set myMenuFlag 1
|
||||||
|
}
|
||||||
|
proc myMenuInvoke {args} {
|
||||||
|
global myMenuFlag myMenuMotion
|
||||||
|
if {$myMenuFlag || $myMenuMotion} {
|
||||||
|
eval ::tk::MenuInvoke $args
|
||||||
|
}
|
||||||
|
set myMenuFlag 0
|
||||||
|
set myMenuMotion 0
|
||||||
|
}
|
||||||
|
proc myMenuMotion {args} {
|
||||||
|
global myMenuFlag myMenuMotion
|
||||||
|
eval ::tk::MenuMotion $args
|
||||||
|
set myMenuMotion 1
|
||||||
|
}
|
||||||
|
proc myMenuLeave {args} {
|
||||||
|
global myMenuFlag myMenuMotion
|
||||||
|
eval ::tk::MenuLeave $args
|
||||||
|
set myMenuMotion 0
|
||||||
|
}
|
||||||
|
bind Menu <Leave> {myMenuLeave %W %X %Y %s}
|
||||||
|
bind Menu <ButtonPress> {myMenuButtonDown %W}
|
||||||
|
bind Menu <ButtonRelease> {myMenuInvoke %W 1}
|
||||||
|
bind Menu <Motion> {myMenuMotion %W %x %y %s}
|
||||||
|
set myMenuFlag 0
|
||||||
|
set myMenuMotion 0
|
||||||
|
|
||||||
|
# ::tk::MenuNextEntry --
|
||||||
|
# Activate the next higher or lower entry in the posted menu,
|
||||||
|
# wrapping around at the ends. Disabled entries are skipped.
|
||||||
|
#
|
||||||
|
# Arguments:
|
||||||
|
# menu - Menu window that received the keystroke.
|
||||||
|
# count - 1 means go to the next lower entry,
|
||||||
|
# -1 means go to the next higher entry.
|
||||||
|
|
||||||
|
proc ::tk::MenuNextEntry {menu count} {
|
||||||
|
global ::tk::Priv
|
||||||
|
|
||||||
|
if {[string equal [$menu index last] "none"]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
set length [expr {[$menu index last]+1}]
|
||||||
|
set quitAfter $length
|
||||||
|
set active [$menu index active]
|
||||||
|
if {[string equal $active "none"]} {
|
||||||
|
set i 0
|
||||||
|
} else {
|
||||||
|
set i [expr {$active + $count}]
|
||||||
|
}
|
||||||
|
while {1} {
|
||||||
|
if {$quitAfter <= 0} {
|
||||||
|
# We've tried every entry in the menu. Either there are
|
||||||
|
# none, or they're all disabled. Just give up.
|
||||||
|
|
||||||
|
return
|
||||||
|
}
|
||||||
|
while {$i < 0} {
|
||||||
|
incr i $length
|
||||||
|
}
|
||||||
|
while {$i >= $length} {
|
||||||
|
incr i -$length
|
||||||
|
}
|
||||||
|
if {[catch {$menu entrycget $i -state} state] == 0} {
|
||||||
|
if {[string compare $state "disabled"]} {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if {$i == $active} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
incr i $count
|
||||||
|
incr quitAfter -1
|
||||||
|
}
|
||||||
|
$menu activate $i
|
||||||
|
::tk::GenerateMenuSelect $menu
|
||||||
|
if {[string equal [$menu type $i] "cascade"]} {
|
||||||
|
set cascade [$menu entrycget $i -menu]
|
||||||
|
if {[string equal [$menu cget -type] "menubar"] && [string compare $cascade ""]} {
|
||||||
|
# Here we auto-post a cascade. This is necessary when
|
||||||
|
# we traverse left/right in the menubar, but undesirable when
|
||||||
|
# we traverse up/down in a menu.
|
||||||
|
$menu postcascade $i
|
||||||
|
::tk::MenuFirstEntry $cascade
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# ::tk::MenuNextMenu --
|
||||||
|
# This procedure is invoked to handle "left" and "right" traversal
|
||||||
|
# motions in menus. It traverses to the next menu in a menu bar,
|
||||||
|
# or into or out of a cascaded menu.
|
||||||
|
#
|
||||||
|
# Arguments:
|
||||||
|
# menu - The menu that received the keyboard
|
||||||
|
# event.
|
||||||
|
# direction - Direction in which to move: "left" or "right"
|
||||||
|
|
||||||
|
proc ::tk::MenuNextMenu {menu direction} {
|
||||||
|
global ::tk::Priv
|
||||||
|
|
||||||
|
# First handle traversals into and out of cascaded menus.
|
||||||
|
|
||||||
|
if {[string equal $direction "right"]} {
|
||||||
|
set count 1
|
||||||
|
set parent [winfo parent $menu]
|
||||||
|
set class [winfo class $parent]
|
||||||
|
if {[string equal [$menu type active] "cascade"]} {
|
||||||
|
$menu postcascade active
|
||||||
|
set m2 [$menu entrycget active -menu]
|
||||||
|
if {[string compare $m2 ""]} {
|
||||||
|
::tk::MenuFirstEntry $m2
|
||||||
|
}
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
set parent [winfo parent $menu]
|
||||||
|
while {[string compare $parent "."]} {
|
||||||
|
if {[string equal [winfo class $parent] "Menu"] \
|
||||||
|
&& [string equal [$parent cget -type] "menubar"]} {
|
||||||
|
tk_menuSetFocus $parent
|
||||||
|
::tk::MenuNextEntry $parent 1
|
||||||
|
return
|
||||||
|
}
|
||||||
|
set parent [winfo parent $parent]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
set count -1
|
||||||
|
set m2 [winfo parent $menu]
|
||||||
|
if {[string equal [winfo class $m2] "Menu"]} {
|
||||||
|
if {[string compare [$m2 cget -type] "menubar"]} {
|
||||||
|
$menu activate none
|
||||||
|
::tk::GenerateMenuSelect $menu
|
||||||
|
tk_menuSetFocus $m2
|
||||||
|
|
||||||
|
# This code unposts any posted submenu in the parent.
|
||||||
|
$m2 postcascade none
|
||||||
|
|
||||||
|
#set tmp [$m2 index active]
|
||||||
|
#$m2 activate none
|
||||||
|
#$m2 activate $tmp
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Can't traverse into or out of a cascaded menu. Go to the next
|
||||||
|
# or previous menubutton, if that makes sense.
|
||||||
|
|
||||||
|
set m2 [winfo parent $menu]
|
||||||
|
if {[string equal [winfo class $m2] "Menu"]} {
|
||||||
|
if {[string equal [$m2 cget -type] "menubar"]} {
|
||||||
|
tk_menuSetFocus $m2
|
||||||
|
::tk::MenuNextEntry $m2 -1
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
set w $::tk::Priv(postedMb)
|
||||||
|
if {[string equal $w ""]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
set buttons [winfo children [winfo parent $w]]
|
||||||
|
set length [llength $buttons]
|
||||||
|
set i [expr {[lsearch -exact $buttons $w] + $count}]
|
||||||
|
while {1} {
|
||||||
|
while {$i < 0} {
|
||||||
|
incr i $length
|
||||||
|
}
|
||||||
|
while {$i >= $length} {
|
||||||
|
incr i -$length
|
||||||
|
}
|
||||||
|
set mb [lindex $buttons $i]
|
||||||
|
if {[string equal [winfo class $mb] "Menubutton"] \
|
||||||
|
&& [string compare [$mb cget -state] "disabled"] \
|
||||||
|
&& [string compare [$mb cget -menu] ""] \
|
||||||
|
&& [string compare [[$mb cget -menu] index last] "none"]} {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if {[string equal $mb $w]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
incr i $count
|
||||||
|
}
|
||||||
|
::tk::MbPost $mb
|
||||||
|
::tk::MenuFirstEntry [$mb cget -menu]
|
||||||
|
}
|
||||||
|
|
||||||
|
# ::tk::MenuFirstEntry --
|
||||||
|
# Given a menu, this procedure finds the first entry that isn't
|
||||||
|
# disabled or a tear-off or separator, and activates that entry.
|
||||||
|
# However, if there is already an active entry in the menu (e.g.,
|
||||||
|
# because of a previous call to ::tk::PostOverPoint) then the active
|
||||||
|
# entry isn't changed. This procedure also sets the input focus
|
||||||
|
# to the menu.
|
||||||
|
#
|
||||||
|
# Arguments:
|
||||||
|
# menu - Name of the menu window (possibly empty).
|
||||||
|
|
||||||
|
proc ::tk::MenuFirstEntry menu {
|
||||||
|
if {[string equal $menu ""]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
tk_menuSetFocus $menu
|
||||||
|
if {[string compare [$menu index active] "none"]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
set last [$menu index last]
|
||||||
|
if {[string equal $last "none"]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
for {set i 0} {$i <= $last} {incr i} {
|
||||||
|
if {([catch {set state [$menu entrycget $i -state]}] == 0) \
|
||||||
|
&& [string compare $state "disabled"]} {
|
||||||
|
#~$menu activate $i
|
||||||
|
#~::tk::GenerateMenuSelect $menu
|
||||||
|
# Only post the cascade if the current menu is a menubar;
|
||||||
|
# otherwise, if the first entry of the cascade is a cascade,
|
||||||
|
# we can get an annoying cascading effect resulting in a bunch of
|
||||||
|
# menus getting posted (bug 676)
|
||||||
|
if {[string equal [$menu type $i] "cascade"] && \
|
||||||
|
[string equal [$menu cget -type] "menubar"]} {
|
||||||
|
set cascade [$menu entrycget $i -menu]
|
||||||
|
if {[string compare $cascade ""]} {
|
||||||
|
$menu postcascade $i
|
||||||
|
::tk::MenuFirstEntry $cascade
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# ::tk::MenuMotion --
|
||||||
|
# This procedure is called to handle mouse motion events for menus.
|
||||||
|
# It does two things. First, it resets the active element in the
|
||||||
|
# menu, if the mouse is over the menu. Second, if a mouse button
|
||||||
|
# is down, it posts and unposts cascade entries to match the mouse
|
||||||
|
# position.
|
||||||
|
#
|
||||||
|
# Arguments:
|
||||||
|
# menu - The menu window.
|
||||||
|
# x - The x position of the mouse.
|
||||||
|
# y - The y position of the mouse.
|
||||||
|
# state - Modifier state (tells whether buttons are down).
|
||||||
|
|
||||||
|
proc ::tk::MenuMotion {menu x y state} {
|
||||||
|
global ::tk::Priv
|
||||||
|
if {$menu eq $::tk::Priv(window)} {
|
||||||
|
if {[$menu cget -type] eq "menubar"} {
|
||||||
|
if {[info exists ::tk::Priv(focus)] && $menu ne $::tk::Priv(focus)} {
|
||||||
|
$menu activate @$x,$y
|
||||||
|
::tk::GenerateMenuSelect $menu
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
$menu activate @$x,$y
|
||||||
|
::tk::GenerateMenuSelect $menu
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#debugmsg plugins "MENU: $menu $::tk::Priv(activeMenu) $::tk::Priv(activeItem) $::tk::Priv(focus)"
|
||||||
|
if {([$menu cget -type] ne "menubar") || \
|
||||||
|
([info exist ::tk::Priv(focus)] && ($::tk::Priv(focus) ne "") && ($::tk::Priv(activeItem) != "none"))} {
|
||||||
|
myMenuPostCascade $menu
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# ::tk::MenuButtonDown --
|
||||||
|
# Handles button presses in menus. There are a couple of tricky things
|
||||||
|
# here:
|
||||||
|
# 1. Change the posted cascade entry (if any) to match the mouse position.
|
||||||
|
# 2. If there is a posted menubutton, must grab to the menubutton; this
|
||||||
|
# overrrides the implicit grab on button press, so that the menu
|
||||||
|
# button can track mouse motions over other menubuttons and change
|
||||||
|
# the posted menu.
|
||||||
|
# 3. If there's no posted menubutton (e.g. because we're a torn-off menu
|
||||||
|
# or one of its descendants) must grab to the top-level menu so that
|
||||||
|
# we can track mouse motions across the entire menu hierarchy.
|
||||||
|
#
|
||||||
|
# Arguments:
|
||||||
|
# menu - The menu window.
|
||||||
|
|
||||||
|
proc ::tk::MenuButtonDown menu {
|
||||||
|
variable ::tk::Priv
|
||||||
|
global tcl_platform
|
||||||
|
|
||||||
|
if {![winfo viewable $menu]} {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
$menu postcascade active
|
||||||
|
if {$Priv(postedMb) ne "" && [winfo viewable $Priv(postedMb)]} {
|
||||||
|
grab -global $Priv(postedMb)
|
||||||
|
} else {
|
||||||
|
while {[$menu cget -type] eq "normal" \
|
||||||
|
&& [winfo class [winfo parent $menu]] eq "Menu" \
|
||||||
|
&& [winfo ismapped [winfo parent $menu]]} {
|
||||||
|
set menu [winfo parent $menu]
|
||||||
|
}
|
||||||
|
|
||||||
|
if {$Priv(menuBar) eq {}} {
|
||||||
|
set Priv(menuBar) $menu
|
||||||
|
set Priv(cursor) [$menu cget -cursor]
|
||||||
|
$menu configure -cursor arrow
|
||||||
|
} else {
|
||||||
|
$menu activate none
|
||||||
|
#MenuUnpost $menu
|
||||||
|
}
|
||||||
|
|
||||||
|
# Don't update grab information if the grab window isn't changing.
|
||||||
|
# Otherwise, we'll get an error when we unpost the menus and
|
||||||
|
# restore the grab, since the old grab window will not be viewable
|
||||||
|
# anymore.
|
||||||
|
|
||||||
|
if {$menu ne [grab current $menu]} {
|
||||||
|
SaveGrabInfo $menu
|
||||||
|
}
|
||||||
|
|
||||||
|
# Must re-grab even if the grab window hasn't changed, in order
|
||||||
|
# to release the implicit grab from the button press.
|
||||||
|
|
||||||
|
if {[tk windowingsystem] eq "x11"} {
|
||||||
|
grab -global $menu
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
set myPriv(id) ""
|
||||||
|
set myPriv(delay) 170
|
||||||
|
set myPriv(activeMenu) ""
|
||||||
|
set myPriv(activeItem) ""
|
||||||
|
|
||||||
|
proc myMenuPostCascade {menu} {
|
||||||
|
global myPriv
|
||||||
|
|
||||||
|
if {$myPriv(id) ne ""} {
|
||||||
|
if {($myPriv(activeMenu) == $menu) && ($myPriv(activeItem) == [$menu index active])} {
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
after cancel $myPriv(id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if {[string equal [$menu cget -type] "menubar"]} {
|
||||||
|
$menu postcascade active
|
||||||
|
} else {
|
||||||
|
set myPriv(activeMenu) $menu
|
||||||
|
set myPriv(activeItem) [$menu index active]
|
||||||
|
set myPriv(id) [after $myPriv(delay) "$menu postcascade active"]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -588,12 +588,12 @@ class Troika(Fan):
|
||||||
self.s.talon.dealRow(rows=[t], frames=4)
|
self.s.talon.dealRow(rows=[t], frames=4)
|
||||||
|
|
||||||
|
|
||||||
class TroikaPlus_RowStack(RK_RowStack):
|
class Quads_RowStack(RK_RowStack):
|
||||||
def getBottomImage(self):
|
def getBottomImage(self):
|
||||||
return self.game.app.images.getReserveBottom()
|
return self.game.app.images.getReserveBottom()
|
||||||
|
|
||||||
class TroikaPlus(Troika):
|
class Quads(Troika):
|
||||||
RowStack_Class = StackWrapper(TroikaPlus_RowStack, dir=0,
|
RowStack_Class = StackWrapper(Quads_RowStack, dir=0,
|
||||||
##base_rank=NO_RANK,
|
##base_rank=NO_RANK,
|
||||||
max_cards=4)
|
max_cards=4)
|
||||||
def createGame(self):
|
def createGame(self):
|
||||||
|
@ -758,8 +758,8 @@ registerGame(GameInfo(385, BoxFan, "Box Fan",
|
||||||
GI.GT_FAN_TYPE | GI.GT_OPEN, 1, 0, GI.SL_MOSTLY_SKILL))
|
GI.GT_FAN_TYPE | GI.GT_OPEN, 1, 0, GI.SL_MOSTLY_SKILL))
|
||||||
registerGame(GameInfo(516, Troika, "Troika",
|
registerGame(GameInfo(516, Troika, "Troika",
|
||||||
GI.GT_FAN_TYPE | GI.GT_OPEN, 1, 0, GI.SL_MOSTLY_SKILL))
|
GI.GT_FAN_TYPE | GI.GT_OPEN, 1, 0, GI.SL_MOSTLY_SKILL))
|
||||||
registerGame(GameInfo(517, TroikaPlus, "Troika +",
|
registerGame(GameInfo(517, Quads, "Quads",
|
||||||
GI.GT_FAN_TYPE | GI.GT_OPEN, 1, 0, GI.SL_MOSTLY_SKILL))
|
GI.GT_FAN_TYPE | GI.GT_OPEN | GI.GT_ORIGINAL, 1, 0, GI.SL_MOSTLY_SKILL))
|
||||||
registerGame(GameInfo(625, FascinationFan, "Fascination Fan",
|
registerGame(GameInfo(625, FascinationFan, "Fascination Fan",
|
||||||
GI.GT_FAN_TYPE, 1, 6, GI.SL_BALANCED))
|
GI.GT_FAN_TYPE, 1, 6, GI.SL_BALANCED))
|
||||||
registerGame(GameInfo(647, Crescent, "Crescent",
|
registerGame(GameInfo(647, Crescent, "Crescent",
|
||||||
|
|
|
@ -23,6 +23,8 @@ import sys, os, locale
|
||||||
import traceback
|
import traceback
|
||||||
import gettext
|
import gettext
|
||||||
|
|
||||||
|
import settings
|
||||||
|
|
||||||
# /***********************************************************************
|
# /***********************************************************************
|
||||||
# // init
|
# // init
|
||||||
# ************************************************************************/
|
# ************************************************************************/
|
||||||
|
@ -50,27 +52,29 @@ def init():
|
||||||
gettext.install('pysol', locale_dir, unicode=True)
|
gettext.install('pysol', locale_dir, unicode=True)
|
||||||
|
|
||||||
## init toolkit
|
## init toolkit
|
||||||
import settings
|
|
||||||
if '--gtk' in sys.argv:
|
if '--gtk' in sys.argv:
|
||||||
settings.TOOLKIT = 'gtk'
|
settings.TOOLKIT = 'gtk'
|
||||||
sys.argv.remove('--gtk')
|
sys.argv.remove('--gtk')
|
||||||
else:
|
elif '--tk' in sys.argv:
|
||||||
if '--tile' in sys.argv:
|
settings.TOOLKIT = 'tk'
|
||||||
|
settings.USE_TILE = False
|
||||||
|
sys.argv.remove('--tk')
|
||||||
|
elif '--tile' in sys.argv:
|
||||||
|
settings.TOOLKIT = 'tk'
|
||||||
|
settings.USE_TILE = True
|
||||||
|
sys.argv.remove('--tile')
|
||||||
|
elif settings.TOOLKIT == 'tk' and settings.USE_TILE == 'auto':
|
||||||
|
# check tile
|
||||||
|
import Tkinter
|
||||||
|
root = Tkinter.Tk()
|
||||||
|
root.withdraw()
|
||||||
|
settings.USE_TILE = False
|
||||||
|
try:
|
||||||
|
root.tk.call('package', 'require', 'tile', '0.7.8')
|
||||||
|
except:
|
||||||
|
pass
|
||||||
|
else:
|
||||||
settings.USE_TILE = True
|
settings.USE_TILE = True
|
||||||
sys.argv.remove('--tile')
|
#root.destroy()
|
||||||
elif settings.USE_TILE == 'auto':
|
Tkinter._default_root = None
|
||||||
# check tile
|
|
||||||
import Tkinter
|
|
||||||
root = Tkinter.Tk()
|
|
||||||
root.withdraw()
|
|
||||||
settings.USE_TILE = False
|
|
||||||
try:
|
|
||||||
tile_version = root.tk.call('package', 'require', 'tile')
|
|
||||||
except:
|
|
||||||
pass
|
|
||||||
else:
|
|
||||||
if tile_version >= '0.7.8':
|
|
||||||
settings.USE_TILE = True
|
|
||||||
#root.destroy()
|
|
||||||
Tkinter._default_root = None
|
|
||||||
|
|
||||||
|
|
|
@ -43,7 +43,7 @@ import gettext
|
||||||
# PySol imports
|
# PySol imports
|
||||||
from mfxutil import destruct, EnvError
|
from mfxutil import destruct, EnvError
|
||||||
from util import CARDSET, DataLoader
|
from util import CARDSET, DataLoader
|
||||||
from settings import PACKAGE, TOOLKIT, VERSION
|
from settings import PACKAGE, TOOLKIT, VERSION, SOUND_MOD
|
||||||
from resource import Tile
|
from resource import Tile
|
||||||
from gamedb import GI
|
from gamedb import GI
|
||||||
from app import Application
|
from app import Application
|
||||||
|
@ -243,29 +243,31 @@ def pysol_init(app, args):
|
||||||
warn_thread = 0
|
warn_thread = 0
|
||||||
warn_pysolsoundserver = 0
|
warn_pysolsoundserver = 0
|
||||||
app.audio = None
|
app.audio = None
|
||||||
if opts["nosound"]:
|
sounds = {'pss': PysolSoundServerModuleClient,
|
||||||
|
'pygame': PyGameAudioClient,
|
||||||
|
'oss': OSSAudioClient,
|
||||||
|
'win': Win32AudioClient}
|
||||||
|
if opts["nosound"] or SOUND_MOD == 'none':
|
||||||
app.audio = AbstractAudioClient()
|
app.audio = AbstractAudioClient()
|
||||||
|
elif opts['sound-mod']:
|
||||||
|
c = sounds[opts['sound-mod']]
|
||||||
|
app.audio = c()
|
||||||
|
elif SOUND_MOD == 'auto':
|
||||||
|
for c in (PysolSoundServerModuleClient,
|
||||||
|
PyGameAudioClient,
|
||||||
|
OSSAudioClient,
|
||||||
|
Win32AudioClient,
|
||||||
|
AbstractAudioClient):
|
||||||
|
try:
|
||||||
|
app.audio = c()
|
||||||
|
except:
|
||||||
|
pass
|
||||||
|
else:
|
||||||
|
# success
|
||||||
|
break
|
||||||
else:
|
else:
|
||||||
if opts['sound-mod']:
|
c = sounds[SOUND_MOD]
|
||||||
d = {'pss': PysolSoundServerModuleClient,
|
app.audio = c()
|
||||||
'pygame': PyGameAudioClient,
|
|
||||||
'oss': OSSAudioClient,
|
|
||||||
'win': Win32AudioClient}
|
|
||||||
c = d[opts['sound-mod']]
|
|
||||||
app.audio = c()
|
|
||||||
else:
|
|
||||||
for c in (PysolSoundServerModuleClient,
|
|
||||||
PyGameAudioClient,
|
|
||||||
OSSAudioClient,
|
|
||||||
Win32AudioClient,
|
|
||||||
AbstractAudioClient):
|
|
||||||
try:
|
|
||||||
app.audio = c()
|
|
||||||
except:
|
|
||||||
pass
|
|
||||||
else:
|
|
||||||
# success
|
|
||||||
break
|
|
||||||
app.audio.startServer()
|
app.audio.startServer()
|
||||||
# update sound_mode
|
# update sound_mode
|
||||||
if isinstance(app.audio, PysolSoundServerModuleClient):
|
if isinstance(app.audio, PysolSoundServerModuleClient):
|
||||||
|
|
|
@ -390,11 +390,7 @@ class OSSAudioClient(AbstractAudioClient):
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
AbstractAudioClient.__init__(self)
|
AbstractAudioClient.__init__(self)
|
||||||
try:
|
import ossaudiodev, wave
|
||||||
import ossaudiodev, wave
|
|
||||||
except:
|
|
||||||
if traceback: traceback.print_exc()
|
|
||||||
raise
|
|
||||||
self.audiodev = ossaudiodev
|
self.audiodev = ossaudiodev
|
||||||
|
|
||||||
def startServer(self):
|
def startServer(self):
|
||||||
|
@ -430,18 +426,14 @@ class PyGameAudioClient(AbstractAudioClient):
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
AbstractAudioClient.__init__(self)
|
AbstractAudioClient.__init__(self)
|
||||||
try:
|
import pygame.mixer, pygame.time
|
||||||
import pygame.mixer, pygame.time
|
if os.name == 'nt':
|
||||||
if os.name == 'nt':
|
# for py2exe
|
||||||
# for py2exe
|
import pygame.base, pygame.rwobject, pygame.mixer_music
|
||||||
import pygame.base, pygame.rwobject, pygame.mixer_music
|
self.mixer = pygame.mixer
|
||||||
self.mixer = pygame.mixer
|
self.mixer.init()
|
||||||
self.mixer.init()
|
self.music = self.mixer.music
|
||||||
self.music = self.mixer.music
|
self.time = pygame.time
|
||||||
self.time = pygame.time
|
|
||||||
except:
|
|
||||||
##if traceback: traceback.print_exc()
|
|
||||||
raise
|
|
||||||
self.audiodev = self.mixer
|
self.audiodev = self.mixer
|
||||||
self.sound = None
|
self.sound = None
|
||||||
self.sound_channel = None
|
self.sound_channel = None
|
||||||
|
|
|
@ -65,6 +65,8 @@ class _MyDialog(gtk.Dialog):
|
||||||
|
|
||||||
|
|
||||||
class MfxDialog(_MyDialog):
|
class MfxDialog(_MyDialog):
|
||||||
|
img = {}
|
||||||
|
button_img = {}
|
||||||
def __init__(self, parent, title='',
|
def __init__(self, parent, title='',
|
||||||
timeout=0,
|
timeout=0,
|
||||||
resizable=0,
|
resizable=0,
|
||||||
|
|
|
@ -23,7 +23,7 @@ import sys, os
|
||||||
|
|
||||||
n_ = lambda x: x # for gettext
|
n_ = lambda x: x # for gettext
|
||||||
|
|
||||||
#
|
|
||||||
#PACKAGE = 'PySolFC'
|
#PACKAGE = 'PySolFC'
|
||||||
PACKAGE = 'PySol'
|
PACKAGE = 'PySol'
|
||||||
PACKAGE_URL = 'http://sourceforge.net/projects/pysolfc/'
|
PACKAGE_URL = 'http://sourceforge.net/projects/pysolfc/'
|
||||||
|
@ -37,6 +37,7 @@ USE_TILE = 'auto' # or True or False
|
||||||
TILE_THEME = 'default' # name of tile's theme
|
TILE_THEME = 'default' # name of tile's theme
|
||||||
if os.name == 'nt':
|
if os.name == 'nt':
|
||||||
TILE_THEME = 'winnative'
|
TILE_THEME = 'winnative'
|
||||||
|
SOUND_MOD = 'auto' # or 'pss', 'pygame', 'oss', 'win', 'none'
|
||||||
|
|
||||||
# data dirs
|
# data dirs
|
||||||
DATA_DIRS = []
|
DATA_DIRS = []
|
||||||
|
|
|
@ -414,6 +414,12 @@ def get_text_width(text, font, root=None):
|
||||||
# ************************************************************************/
|
# ************************************************************************/
|
||||||
|
|
||||||
def load_theme(app, top, theme):
|
def load_theme(app, top, theme):
|
||||||
|
#
|
||||||
|
if os.name == 'posix':
|
||||||
|
f = os.path.join(app.dataloader.dir, 'tcl', 'menu8.4.tcl')
|
||||||
|
if os.path.exists(f):
|
||||||
|
top.tk.call('source', f)
|
||||||
|
#
|
||||||
top.tk.call("package", "require", "tile")
|
top.tk.call("package", "require", "tile")
|
||||||
# load available themes
|
# load available themes
|
||||||
d = os.path.join(app.dataloader.dir, 'themes')
|
d = os.path.join(app.dataloader.dir, 'themes')
|
||||||
|
|
|
@ -43,7 +43,7 @@ __all__ = ['MfxDialog',
|
||||||
]
|
]
|
||||||
|
|
||||||
# imports
|
# imports
|
||||||
import os, sys, time, types
|
import os, sys, time, locale
|
||||||
import Tkinter as Tk
|
import Tkinter as Tk
|
||||||
import Tile as Tkinter
|
import Tile as Tkinter
|
||||||
import traceback
|
import traceback
|
||||||
|
@ -103,28 +103,7 @@ class MfxDialog: # ex. _ToplevelDialog
|
||||||
def destroy(self):
|
def destroy(self):
|
||||||
after_cancel(self.timer)
|
after_cancel(self.timer)
|
||||||
unbind_destroy(self.top)
|
unbind_destroy(self.top)
|
||||||
try:
|
self.top.destroy()
|
||||||
self.top.wm_withdraw()
|
|
||||||
except:
|
|
||||||
if traceback: traceback.print_exc()
|
|
||||||
pass
|
|
||||||
try:
|
|
||||||
self.top.destroy()
|
|
||||||
except:
|
|
||||||
if traceback: traceback.print_exc()
|
|
||||||
pass
|
|
||||||
#destruct(self.top)
|
|
||||||
if 1 and self.parent: # ???
|
|
||||||
try:
|
|
||||||
##self.parent.update_idletasks()
|
|
||||||
# FIXME: why do we need this under Windows ?
|
|
||||||
if hasattr(self.parent, "busyUpdate"):
|
|
||||||
self.parent.busyUpdate()
|
|
||||||
else:
|
|
||||||
self.parent.update()
|
|
||||||
except:
|
|
||||||
if traceback: traceback.print_exc()
|
|
||||||
pass
|
|
||||||
self.top = None
|
self.top = None
|
||||||
self.parent = None
|
self.parent = None
|
||||||
|
|
||||||
|
@ -147,11 +126,18 @@ class MfxDialog: # ex. _ToplevelDialog
|
||||||
|
|
||||||
def altKeyEvent(self, event):
|
def altKeyEvent(self, event):
|
||||||
key = event.char
|
key = event.char
|
||||||
key = unicode(key, 'utf-8')
|
try:
|
||||||
key = key.lower()
|
if os.name == 'nt':
|
||||||
widget = self.accel_keys.get(key)
|
key = unicode(key, locale.getpreferredencoding())
|
||||||
if not widget is None:
|
else:
|
||||||
widget.event_generate('<<Invoke>>')
|
key = unicode(key, 'utf-8')
|
||||||
|
except:
|
||||||
|
pass
|
||||||
|
else:
|
||||||
|
key = key.lower()
|
||||||
|
widget = self.accel_keys.get(key)
|
||||||
|
if not widget is None:
|
||||||
|
widget.event_generate('<<Invoke>>')
|
||||||
|
|
||||||
def initKw(self, kw):
|
def initKw(self, kw):
|
||||||
kw = KwStruct(kw,
|
kw = KwStruct(kw,
|
||||||
|
@ -196,12 +182,9 @@ class MfxDialog: # ex. _ToplevelDialog
|
||||||
focus = None
|
focus = None
|
||||||
max_len = 0
|
max_len = 0
|
||||||
for s in kw.strings:
|
for s in kw.strings:
|
||||||
if type(s) is types.TupleType:
|
if type(s) is tuple:
|
||||||
s = s[0]
|
s = s[0]
|
||||||
if s:
|
if s:
|
||||||
##s = re.sub(r"[\s\.\,]", "", s)
|
|
||||||
#if os.name == 'posix':
|
|
||||||
# s = s.replace('...', '.')
|
|
||||||
s = s.replace('&', '')
|
s = s.replace('&', '')
|
||||||
max_len = max(max_len, len(s))
|
max_len = max(max_len, len(s))
|
||||||
##print s, len(s)
|
##print s, len(s)
|
||||||
|
@ -212,7 +195,7 @@ class MfxDialog: # ex. _ToplevelDialog
|
||||||
#
|
#
|
||||||
for s in kw.strings:
|
for s in kw.strings:
|
||||||
xbutton = button = button + 1
|
xbutton = button = button + 1
|
||||||
if type(s) is types.TupleType:
|
if type(s) is tuple:
|
||||||
assert len(s) == 2
|
assert len(s) == 2
|
||||||
button = int(s[1])
|
button = int(s[1])
|
||||||
s = s[0]
|
s = s[0]
|
||||||
|
@ -228,7 +211,7 @@ class MfxDialog: # ex. _ToplevelDialog
|
||||||
button = xbutton
|
button = xbutton
|
||||||
else:
|
else:
|
||||||
widget = Tkinter.Button(frame, text=s, default="normal",
|
widget = Tkinter.Button(frame, text=s, default="normal",
|
||||||
command=(lambda self=self, button=button: self.mDone(button)))
|
command=(lambda self=self, button=button: self.mDone(button)))
|
||||||
if button == kw.default:
|
if button == kw.default:
|
||||||
focus = widget
|
focus = widget
|
||||||
focus.config(default="active")
|
focus.config(default="active")
|
||||||
|
@ -429,7 +412,7 @@ class MfxTooltip:
|
||||||
|
|
||||||
class MfxScrolledCanvas:
|
class MfxScrolledCanvas:
|
||||||
def __init__(self, parent, hbar=2, vbar=2, **kw):
|
def __init__(self, parent, hbar=2, vbar=2, **kw):
|
||||||
kwdefault(kw, borderwidth=1, relief='sunken')
|
kwdefault(kw, highlightthickness=0, bd=1, relief='sunken')
|
||||||
self.parent = parent
|
self.parent = parent
|
||||||
self.createFrame(kw)
|
self.createFrame(kw)
|
||||||
self.canvas = None
|
self.canvas = None
|
||||||
|
|
|
@ -76,16 +76,17 @@ class AbstractToolbarButton:
|
||||||
if self.visible and not force:
|
if self.visible and not force:
|
||||||
return
|
return
|
||||||
self.visible = True
|
self.visible = True
|
||||||
padx, pady = 2, 2
|
|
||||||
if orient == Tkinter.HORIZONTAL:
|
if orient == Tkinter.HORIZONTAL:
|
||||||
|
padx, pady = 0, 2
|
||||||
self.grid(row=0,
|
self.grid(row=0,
|
||||||
column=self.position,
|
column=self.position,
|
||||||
ipadx=padx, ipady=pady,
|
padx=padx, pady=pady,
|
||||||
sticky='nsew')
|
sticky='nsew')
|
||||||
else:
|
else:
|
||||||
|
padx, pady = 2, 0
|
||||||
self.grid(row=self.position,
|
self.grid(row=self.position,
|
||||||
column=0,
|
column=0,
|
||||||
ipadx=padx, ipady=pady,
|
padx=padx, pady=pady,
|
||||||
sticky='nsew')
|
sticky='nsew')
|
||||||
|
|
||||||
def hide(self):
|
def hide(self):
|
||||||
|
@ -273,9 +274,10 @@ class PysolToolbar(PysolToolbarActions):
|
||||||
# Change the look of the frame to match the platform look
|
# Change the look of the frame to match the platform look
|
||||||
# (see also setRelief)
|
# (see also setRelief)
|
||||||
if os.name == 'posix':
|
if os.name == 'posix':
|
||||||
|
##self.frame.config(bd=1, relief=self.frame_relief)
|
||||||
pass
|
pass
|
||||||
elif os.name == "nt":
|
elif os.name == "nt":
|
||||||
self.frame.config(relief=self.frame_relief)
|
self.frame.config(bd=2, relief=self.frame_relief, padx=2, pady=2)
|
||||||
else:
|
else:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
@ -323,7 +325,7 @@ class PysolToolbar(PysolToolbarActions):
|
||||||
self.frame_relief = 'groove'
|
self.frame_relief = 'groove'
|
||||||
else:
|
else:
|
||||||
self.frame_relief = 'raised'
|
self.frame_relief = 'raised'
|
||||||
self.separator_relief = 'sunken' #'raised'
|
self.separator_relief = 'sunken'
|
||||||
if os.name == 'nt':
|
if os.name == 'nt':
|
||||||
self.frame_relief = 'groove'
|
self.frame_relief = 'groove'
|
||||||
self.separator_relief = 'groove'
|
self.separator_relief = 'groove'
|
||||||
|
@ -373,7 +375,6 @@ class PysolToolbar(PysolToolbarActions):
|
||||||
name = label.lower()
|
name = label.lower()
|
||||||
image = self._loadImage(name)
|
image = self._loadImage(name)
|
||||||
position = len(self._widgets)
|
position = len(self._widgets)
|
||||||
bd = self.button_relief == 'flat' and 1 or 2
|
|
||||||
kw = {
|
kw = {
|
||||||
'position' : position,
|
'position' : position,
|
||||||
'toolbar' : self,
|
'toolbar' : self,
|
||||||
|
@ -381,20 +382,10 @@ class PysolToolbar(PysolToolbarActions):
|
||||||
'command' : command,
|
'command' : command,
|
||||||
'takefocus' : 0,
|
'takefocus' : 0,
|
||||||
'text' : gettext(label),
|
'text' : gettext(label),
|
||||||
'bd' : bd,
|
|
||||||
'relief' : self.button_relief,
|
|
||||||
'padx' : self.button_pad,
|
|
||||||
'pady' : self.button_pad
|
|
||||||
}
|
}
|
||||||
if Tkinter.TkVersion >= 8.4:
|
|
||||||
kw['overrelief'] = 'raised'
|
|
||||||
if image:
|
if image:
|
||||||
kw['image'] = image
|
kw['image'] = image
|
||||||
if check:
|
if check:
|
||||||
if Tkinter.TkVersion >= 8.4:
|
|
||||||
kw['offrelief'] = self.button_relief
|
|
||||||
kw['indicatoron'] = False
|
|
||||||
kw['selectcolor'] = ''
|
|
||||||
button = ToolbarCheckbutton(self.frame, **kw)
|
button = ToolbarCheckbutton(self.frame, **kw)
|
||||||
else:
|
else:
|
||||||
button = ToolbarButton(self.frame, **kw)
|
button = ToolbarButton(self.frame, **kw)
|
||||||
|
|
Loading…
Add table
Reference in a new issue