## vim:ts=4:et:nowrap ## ##---------------------------------------------------------------------------## ## ## PySol -- a Python Solitaire game ## ## Copyright (C) 2003 Markus Franz Xaver Johannes Oberhumer ## Copyright (C) 2002 Markus Franz Xaver Johannes Oberhumer ## Copyright (C) 2001 Markus Franz Xaver Johannes Oberhumer ## Copyright (C) 2000 Markus Franz Xaver Johannes Oberhumer ## Copyright (C) 1999 Markus Franz Xaver Johannes Oberhumer ## Copyright (C) 1998 Markus Franz Xaver Johannes Oberhumer ## All Rights Reserved. ## ## 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 2 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; see the file COPYING. ## If not, write to the Free Software Foundation, Inc., ## 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. ## ## Markus F.X.J. Oberhumer ## ## http://www.oberhumer.com/pysol ## ##---------------------------------------------------------------------------## # imports import math, os, re, string, sys, types import Tkinter, tkColorChooser, tkFileDialog # PySol imports from mfxtools import * from mfxutil import destruct, Struct, kwdefault from util import PACKAGE, VERSION, CARDSET, bundle from gamedb import GI from actions import PysolMenubarActions from pysolaudio import pysolsoundserver # toolkit imports from tkconst import EVENT_HANDLED, EVENT_PROPAGATE, CURSOR_WATCH from tkutil import bind, after_idle from selectgame import SelectGameDialog, SelectGameDialogWithPreview from selectcardset import SelectCardsetDialogWithPreview from selectcardset import SelectCardsetByTypeDialogWithPreview from selecttile import SelectTileDialogWithPreview # /*********************************************************************** # // # ************************************************************************/ class MfxMenubar(Tkinter.Menu): addPath = None def __init__(self, master, **kw): assert kw.get("name") self.n = kw["tearoff"] = int(kw.get("tearoff", 0)) apply(Tkinter.Menu.__init__, (self, master, ), kw) def labeltoname(self, label): underline = -1 m = re.search(r"^(.*)\&([^\&].*)$", label) if m: l1, l2 = m.group(1), m.group(2) l1 = re.sub(r"\&\&", "&", l1) l2 = re.sub(r"\&\&", "&", l2) label = l1 + l2 underline = len(l1) name = string.lower(re.sub(r"[^0-9a-zA-Z]", "", label)) return name, label, underline def add(self, itemType, cnf={}): label = cnf.get("label") if label: name, label, underline = self.labeltoname(label) cnf["label"] = label cnf["underline"] = cnf.get("underline", underline) path = str(self._w) + "." + name if self.addPath: self.addPath(path, self, self.n, cnf.get("menu")) if os.name == "posix": pass ## cnf["relief"] = "groove" ## cnf["activeforeground"] = "#ff0000" Tkinter.Menu.add(self, itemType, cnf) self.n = self.n + 1 class MfxMenu(MfxMenubar): def __init__(self, master, label, underline=None, **kw): name, label, label_underline = self.labeltoname(label) kwdefault(kw, name=name) if 1 and os.name == "posix": pass ## kw["relief"] = "groove" ## kw["activeborderwidth"] = 1 apply(MfxMenubar.__init__, (self, master,), kw) if underline is None: underline = label_underline master.add_cascade(menu=self, label=label, underline=underline) # /*********************************************************************** # // - create menubar # // - update menubar # // - menu actions # ************************************************************************/ class PysolMenubar(PysolMenubarActions): def __init__(self, app, top): PysolMenubarActions.__init__(self, app, top) # init columnbreak sh = self.top.winfo_screenheight() self.__cb_max = 25 if sh >= 600: self.__cb_max = 30 if sh >= 768: self.__cb_max = 35 # create menus self.__menubar = None self.__menupath = {} self.__keybindings = {} self._createMenubar() # set the menubar self.updateBackgroundImagesMenu() self.top.config(menu=self.__menubar) # create a GTK-like path def _addPath(self, path, menu, index, submenu): if not self.__menupath.has_key(path): ##print path, menu, index, submenu self.__menupath[path] = (menu, index, submenu) def _getEnabledState(self, enabled): if enabled: return "normal" return "disabled" # # create the menubar # def _createMenubar(self): MfxMenubar.addPath = self._addPath kw = { "name": "menubar" } if 1 and os.name == "posix": pass kw["relief"] = "groove" kw["activeborderwidth"] = 1 self.__menubar = apply(MfxMenubar, (self.top,), kw) # init keybindings bind(self.top, "", self._keyPressHandler) m = "Ctrl-" if os.name == "mac": m = "Cmd-" menu = self._createMenu("&File") menu.add_command(label="&New game", command=self.mNewGame, accelerator="N") submenu = MfxMenu(menu, label="R&ecent games") menu.add_command(label="Select &random game", command=self.mSelectRandomGame, accelerator=m+"R") menu.add_command(label="Select game by nu&mber...", command=self.mSelectGameById, accelerator=m+"M") menu.add_separator() menu.add_command(label="&Open...", command=self.mOpen, accelerator=m+"O") menu.add_command(label="&Save", command=self.mSave, accelerator=m+"S") menu.add_command(label="Save &as...", command=self.mSaveAs) menu.add_separator() menu.add_command(label="&Hold and quit", command=self.mHoldAndQuit) menu.add_command(label="&Quit", command=self.mQuit, accelerator=m+"Q") menu = self._createMenu("&Select") self._addSelectGameMenu(menu) menu = self._createMenu("&Edit") menu.add_command(label="&Undo", command=self.mUndo, accelerator="Z") menu.add_command(label="&Redo", command=self.mRedo, accelerator="R") menu.add_command(label="Redo &all", command=self.mRedoAll) menu.add_separator() submenu = MfxMenu(menu, label="&Set bookmark") for i in range(9): label = "Bookmark %d" % (i + 1) submenu.add_command(label=label, command=lambda self=self, i=i: self.mSetBookmark(i)) submenu = MfxMenu(menu, label="Go&to bookmark") for i in range(9): label = "Bookmark %d" % (i + 1) acc = m + "%d" % (i + 1) submenu.add_command(label=label, command=lambda self=self, i=i: self.mGotoBookmark(i), accelerator=acc) menu.add_command(label="&Clear bookmarks", command=self.mClearBookmarks) menu.add_separator() menu.add_command(label="Restart &game", command=self.mRestart, accelerator=m+"G") menu = self._createMenu("&Game") if PACKAGE != "PyJongg": menu.add_command(label="&Deal cards", command=self.mDeal, accelerator="D") menu.add_command(label="&Auto drop", command=self.mDrop, accelerator="A") menu.add_separator() menu.add_command(label="S&tatus...", command=self.mStatus, accelerator="T") menu.add_checkbutton(label="&Comments...", variable=self.tkopt.comment, command=self.mEditGameComment) menu.add_separator() submenu = MfxMenu(menu, label="&Statistics") submenu.add_command(label="Current game...", command=lambda self=self: self.mPlayerStats(mode=101)) submenu.add_command(label="All games...", command=lambda self=self: self.mPlayerStats(mode=102)) submenu.add_separator() submenu.add_command(label="Session log...", command=lambda self=self: self.mPlayerStats(mode=104)) submenu.add_command(label="Full log...", command=lambda self=self: self.mPlayerStats(mode=103)) submenu = MfxMenu(menu, label="Demo statistics") submenu.add_command(label="Current game...", command=lambda self=self: self.mPlayerStats(mode=1101)) submenu.add_command(label="All games...", command=lambda self=self: self.mPlayerStats(mode=1102)) menu = self._createMenu("&Assist") menu.add_command(label="&Hint", command=self.mHint, accelerator="H") if PACKAGE == "PyJongg": menu.add_command(label="Highlight t&iles", command=self.mHighlightPiles, accelerator="I") else: menu.add_command(label="Highlight p&iles", command=self.mHighlightPiles, accelerator="I") menu.add_separator() menu.add_command(label="&Demo", command=self.mDemo, accelerator=m+"D") menu.add_command(label="Demo (&all games)", command=self.mMixedDemo) menu = self._createMenu("&Options") menu.add_command(label="&Player options...", command=self.mOptPlayerOptions) if PACKAGE == "PyJongg": submenu = MfxMenu(menu, label="Assist &level") submenu.add_checkbutton(label="Enable &undo", variable=self.tkopt.undo, command=self.mOptEnableUndo) submenu.add_checkbutton(label="Enable &bookmarks", variable=self.tkopt.bookmarks, command=self.mOptEnableBookmarks) submenu.add_checkbutton(label="Enable &hint", variable=self.tkopt.hint, command=self.mOptEnableHint) submenu.add_checkbutton(label="Enable highlight t&iles", variable=self.tkopt.highlight_piles, command=self.mOptEnableHighlightPiles) else: submenu = MfxMenu(menu, label="&Automatic play") submenu.add_checkbutton(label="Auto &face up", variable=self.tkopt.autofaceup, command=self.mOptAutoFaceUp) submenu.add_checkbutton(label="&Auto drop", variable=self.tkopt.autodrop, command=self.mOptAutoDrop) submenu.add_checkbutton(label="Auto &deal", variable=self.tkopt.autodeal, command=self.mOptAutoDeal) submenu.add_separator() submenu.add_checkbutton(label="&Quick play", variable=self.tkopt.quickplay, command=self.mOptQuickPlay) submenu = MfxMenu(menu, label="Assist &level") submenu.add_checkbutton(label="Enable &undo", variable=self.tkopt.undo, command=self.mOptEnableUndo) submenu.add_checkbutton(label="Enable &bookmarks", variable=self.tkopt.bookmarks, command=self.mOptEnableBookmarks) submenu.add_checkbutton(label="Enable &hint", variable=self.tkopt.hint, command=self.mOptEnableHint) submenu.add_checkbutton(label="Enable highlight p&iles", variable=self.tkopt.highlight_piles, command=self.mOptEnableHighlightPiles) submenu.add_checkbutton(label="Enable highlight &cards", variable=self.tkopt.highlight_cards, command=self.mOptEnableHighlightCards) submenu.add_checkbutton(label="Enable highlight same &rank", variable=self.tkopt.highlight_samerank, command=self.mOptEnableHighlightSameRank) menu.add_separator() if self.app.audio.audiodev is None: menu.add_checkbutton(label="&Sound", variable=self.tkopt.sound, command=self.mOptSound, state=Tkinter.DISABLED) elif pysolsoundserver: menu.add_checkbutton(label="&Sound...", variable=self.tkopt.sound, command=self.mOptSoundDialog) else: menu.add_checkbutton(label="&Sound", variable=self.tkopt.sound, command=self.mOptSound) # cardsets manager = self.app.cardset_manager n = manager.len() if PACKAGE == "PyJongg": menu.add_command(label="Tiles&et...", command=self.mSelectCardsetDialog, accelerator="E") # this submenu will get set by updateBackgroundImagesMenu() submenu = MfxMenu(menu, label="Tile &border") menu.add_command(label="Table b&ackground...", command=self.mSelectTileDialog) else: menu.add_command(label="Cards&et...", command=self.mSelectCardsetDialog, accelerator="E") # this submenu will get set by updateBackgroundImagesMenu() submenu = MfxMenu(menu, label="Card &background") menu.add_command(label="Table t&ile...", command=self.mSelectTileDialog) submenu = MfxMenu(menu, label="A&nimations") submenu.add_radiobutton(label="&None", variable=self.tkopt.animations, value=0, command=self.mOptAnimations) submenu.add_radiobutton(label="&Timer based", variable=self.tkopt.animations, value=2, command=self.mOptAnimations) submenu.add_radiobutton(label="&Fast", variable=self.tkopt.animations, value=1, command=self.mOptAnimations) submenu.add_radiobutton(label="&Slow", variable=self.tkopt.animations, value=3, command=self.mOptAnimations) submenu.add_radiobutton(label="&Very slow", variable=self.tkopt.animations, value=4, command=self.mOptAnimations) if PACKAGE != "PyJongg": menu.add_checkbutton(label="Card shado&w", variable=self.tkopt.shadow, command=self.mOptShadow) menu.add_checkbutton(label="Shade &legal moves", variable=self.tkopt.shade, command=self.mOptShade) menu.add_separator() menu.add_command(label="&Hint options...", command=self.mOptHintOptions) menu.add_command(label="&Demo options...", command=self.mOptDemoOptions) menu.add_separator() submenu = MfxMenu(menu, label="&Toolbar") submenu.add_radiobutton(label="&Hide", variable=self.tkopt.toolbar, value=0, command=self.mOptToolbar) submenu.add_radiobutton(label="&Top", variable=self.tkopt.toolbar, value=1, command=self.mOptToolbar) submenu.add_radiobutton(label="&Bottom", variable=self.tkopt.toolbar, value=2, command=self.mOptToolbar) submenu.add_separator() submenu.add_radiobutton(label="&Small icons", variable=self.tkopt.toolbar_size, value=0, command=self.mOptToolbarSize) submenu.add_radiobutton(label="&Large icons", variable=self.tkopt.toolbar_size, value=1, command=self.mOptToolbarSize) menu.add_checkbutton(label="Stat&usbar", variable=self.tkopt.statusbar, command=self.mOptStatusbar) ### menu.add_separator() ### menu.add_command(label="Save options", command=self.mOptSave) menu = self._createMenu("&Help") menu.add_command(label="&Contents", command=self.mHelp, accelerator=m+"F1") menu.add_command(label="&How to play", command=self.mHelpHowToPlay) menu.add_command(label="&Rules for this game", command=self.mHelpRules, accelerator="F1") if bundle & 4 == 0: menu.add_command(label="&License terms", command=self.mHelpLicense) menu.add_command(label="What's &new ?", command=self.mHelpNews) menu.add_separator() menu.add_command(label="&About "+PACKAGE+"...", command=self.mHelpAbout) MfxMenubar.addPath = None ### FIXME: all key bindings should be *added* to keyPressHandler ctrl = "Control-" self._bindKey("", "n", self.mNewGame) self._bindKey("", "g", self.mSelectGameDialog) self._bindKey("", "v", self.mSelectGameDialogWithPreview) self._bindKey(ctrl, "r", self.mSelectRandomGame) self._bindKey(ctrl, "m", self.mSelectGameById) self._bindKey(ctrl, "n", self.mNewGameWithNextId) self._bindKey(ctrl, "o", self.mOpen) ##self._bindKey("", "F3", self.mOpen) # undocumented self._bindKey(ctrl, "s", self.mSave) ##self._bindKey("", "F2", self.mSaveAs) # undocumented self._bindKey(ctrl, "q", self.mQuit) self._bindKey("", "z", self.mUndo) self._bindKey("", "BackSpace", self.mUndo) # undocumented self._bindKey("", "r", self.mRedo) self._bindKey(ctrl, "g", self.mRestart) self._bindKey("", "space", self.mDeal) # undocumented self._bindKey("", "t", self.mStatus) self._bindKey(ctrl, "t", self.mPlayerStats) # undocumented self._bindKey("", "h", self.mHint) self._bindKey(ctrl, "h", self.mHint1) # undocumented ##self._bindKey("", "Shift_L", self.mHighlightPiles) ##self._bindKey("", "Shift_R", self.mHighlightPiles) self._bindKey("", "i", self.mHighlightPiles) self._bindKey(ctrl, "d", self.mDemo) self._bindKey("", "e", self.mSelectCardsetDialog) self._bindKey(ctrl, "b", self.mOptChangeCardback) # undocumented self._bindKey(ctrl, "i", self.mOptChangeTableTile) # undocumented self._bindKey(ctrl, "p", self.mOptPlayerOptions) # undocumented self._bindKey(ctrl, "F1", self.mHelp) self._bindKey("", "F1", self.mHelpRules) self._bindKey("", "Print", self.mScreenshot) self._bindKey(ctrl, "u", self.mPlayNextMusic) # undocumented # ASD and LKJ self._bindKey("", "a", self.mDrop) self._bindKey(ctrl, "a", self.mDrop1) self._bindKey("", "s", self.mUndo) self._bindKey("", "d", self.mDeal) self._bindKey("", "l", self.mDrop) self._bindKey(ctrl, "l", self.mDrop1) self._bindKey("", "k", self.mUndo) self._bindKey("", "j", self.mDeal) for i in range(9): self._bindKey(ctrl, str(i+1), lambda event, self=self, i=i: self.mGotoBookmark(i, confirm=0)) if 1 and self.app.debug: self._bindKey(ctrl, "End", self.mPlayNextMusic) self._bindKey(ctrl, "Prior", self.mSelectPrevGameByName) self._bindKey(ctrl, "Next", self.mSelectNextGameByName) self._bindKey(ctrl, "Up", self.mSelectPrevGameById) self._bindKey(ctrl, "Down", self.mSelectNextGameById) # # key binding utility # def _bindKey(self, modifier, key, func): if 0 and not modifier and len(key) == 1: self.__keybindings[string.lower(key)] = func self.__keybindings[string.upper(key)] = func return sequence = "<" + modifier + "KeyPress-" + key + ">" try: bind(self.top, sequence, func) if len(key) == 1 and key != string.upper(key): key = string.upper(key) sequence = "<" + modifier + "KeyPress-" + key + ">" bind(self.top, sequence, func) except: raise #bundle# pass def _keyPressHandler(self, event): r = EVENT_PROPAGATE if event and self.game: ##print event.__dict__ if self.game.demo: # stop the demo by setting self.game.demo.keypress if event.char: # ignore Ctrl/Shift/etc. self.game.demo.keypress = event.char r = EVENT_HANDLED func = self.__keybindings.get(event.char) if func and (event.state & ~2) == 0: func(event) r = EVENT_HANDLED return r # utility def _createMenu(self, label): # It took me hours to find out how to place the help-menu # on the right side of the menubar. Finally I discovered # that there seems to be some magic with the widget name... tearoff = 0 if os.name == "nt": tearoff = 1 menu = MfxMenu(self.__menubar, label, tearoff=tearoff, underline=-1) return menu # # Select Game menu creation # def _addSelectGameMenu(self, menu): games = map(self.app.gdb.get, self.app.gdb.getGamesIdSortedByShortName()) games = tuple(games) ###menu = MfxMenu(menu, label="Select &game") menu.add_command(label="All &games...", command=self.mSelectGameDialog, accelerator="G") menu.add_command(label="Playable pre&view...", command=self.mSelectGameDialogWithPreview, accelerator="V") menu.add_separator() data = ("&Popular games", lambda gi: gi.si.game_flags & GI.GT_POPULAR) self._addSelectGameSubMenu(menu, games, (data, ), self.mSelectGamePopular, self.tkopt.gameid_popular) if PACKAGE == "PyJongg": menu.add_separator() self._addSelectMahjonggGameSubMenu(menu, games, self.mSelectGame, self.tkopt.gameid) return ##menu.add_separator() submenu = MfxMenu(menu, label="&Special games") self._addSelectGameSubMenu(submenu, games, GI.SELECT_SPECIAL_GAME_BY_TYPE, self.mSelectGame, self.tkopt.gameid) menu.add_separator() self._addSelectGameSubMenu(menu, games, GI.SELECT_GAME_BY_TYPE, self.mSelectGame, self.tkopt.gameid) def _addSelectGameSubMenu(self, menu, games, select_data, command, variable): ##print select_data need_sep = 0 for label, select_func in select_data: if label is None: need_sep = 1 continue g = filter(select_func, games) if not g: continue if need_sep: menu.add_separator() need_sep = 0 submenu = MfxMenu(menu, label=label) if 1 and label == "Mahjongg type": ##self._addSelectMahjonggGameSubMenu(submenu, g, command, variable) pass else: self._addSelectGameSubSubMenu(submenu, g, command, variable) def _addSelectMahjonggGameSubMenu(self, menu, g, command, variable): for c in ("AC", "DF", "GK", "LR", "ST", "UZ"): gg = filter(lambda gi, c0=c[0], c1=c[1]: c0 <= gi.short_name[0] <= c1, g) if not gg: continue label = c[0] if c[0] != c[1]: label = c[0] + " - " + c[1] submenu = MfxMenu(menu, label=label) self._addSelectGameSubSubMenu(submenu, gg, command, variable) def _addSelectGameSubSubMenu(self, menu, g, command, variable): cb = (25, self.__cb_max) [ len(g) > 4 * 25 ] for i in range(len(g)): gi = g[i] columnbreak = i > 0 and (i % cb) == 0 menu.add_radiobutton(command=command, variable=variable, columnbreak=columnbreak, value=gi.id, label=gi.short_name) # # Select Game menu actions # def _mSelectGameDialog(self, d): if d.status == 0 and d.button == 0 and d.gameid != self.game.id: self.tkopt.gameid.set(d.gameid) self.tkopt.gameid_popular.set(d.gameid) if 0: self._mSelectGame(d.gameid, random=d.random) else: # don't ask areYouSure() self.game.endGame() self.game.quitGame(d.gameid, random=d.random) return EVENT_HANDLED def __restoreCursor(self, *event): self.game.setCursor(cursor=self.app.top_cursor) def mSelectGameDialog(self, *event): if self._cancelDrag(): return self.game.setCursor(cursor=CURSOR_WATCH) after_idle(self.top, self.__restoreCursor) d = SelectGameDialog(self.top, title="Select game", app=self.app, gameid=self.game.id) return self._mSelectGameDialog(d) def mSelectGameDialogWithPreview(self, *event): if self._cancelDrag(): return self.game.setCursor(cursor=CURSOR_WATCH) bookmark = None if 0: # use a bookmark for our preview game if self.game.setBookmark(-2, confirm=0): bookmark = self.game.gsaveinfo.bookmarks[-2][0] del self.game.gsaveinfo.bookmarks[-2] after_idle(self.top, self.__restoreCursor) d = SelectGameDialogWithPreview(self.top, title="Select game", app=self.app, gameid=self.game.id, bookmark=bookmark) return self._mSelectGameDialog(d) # # menubar overrides # def updateRecentGamesMenu(self, gameids): # delete all entries submenu = self.__menupath[".menubar.file.recentgames"][2] submenu.delete(0, "last") # insert games cb = (25, self.__cb_max) [ len(gameids) > 4 * 25 ] i = 0 for id in gameids: gi = self.app.getGameInfo(id) if not gi: continue columnbreak = i > 0 and (i % cb) == 0 submenu.add_radiobutton(command=self.mSelectGame, variable=self.tkopt.gameid, columnbreak=columnbreak, value=gi.id, label=gi.short_name) i = i + 1 def updateBookmarkMenuState(self): state = self._getEnabledState mp1 = self.__menupath.get(".menubar.edit.setbookmark") mp2 = self.__menupath.get(".menubar.edit.gotobookmark") mp3 = self.__menupath.get(".menubar.edit.clearbookmarks") if mp1 is None or mp2 is None or mp3 is None: return x = self.app.opt.bookmarks and self.game.canSetBookmark() # menu, index, submenu = mp1 for i in range(9): submenu.entryconfig(i, state=state(x)) menu.entryconfig(index, state=state(x)) # menu, index, submenu = mp2 ms = 0 for i in range(9): s = self.game.gsaveinfo.bookmarks.get(i) is not None submenu.entryconfig(i, state=state(s and x)) ms = ms or s menu.entryconfig(index, state=state(ms and x)) # menu, index, submenu = mp3 menu.entryconfig(index, state=state(ms and x)) def updateBackgroundImagesMenu(self): mp = self.__menupath.get(".menubar.options.cardbackground") if PACKAGE == "PyJongg" and mp is None: mp = self.__menupath.get(".menubar.options.tileborder") # delete all entries submenu = mp[2] submenu.delete(0, "last") # insert new cardbacks mbacks = self.app.images.getCardbacks() cb = int(math.ceil(math.sqrt(len(mbacks)))) for i in range(len(mbacks)): columnbreak = i > 0 and (i % cb) == 0 submenu.add_radiobutton(label=mbacks[i].name, image=mbacks[i].menu_image, variable=self.tkopt.cardback, value=i, command=self.mOptCardback, columnbreak=columnbreak, indicatoron=0, hidemargin=0) # # menu updates # def setMenuState(self, state, path): #print state, path path = ".menubar." + path mp = self.__menupath.get(path) if PACKAGE == "PyJongg" and mp is None: return menu, index, submenu = mp s = self._getEnabledState(state) menu.entryconfig(index, state=s) def setToolbarState(self, state, path): #print state, path s = self._getEnabledState(state) w = getattr(self.app.toolbar, path + "_button") w["state"] = s # # menu actions # if PACKAGE == "PyJongg": DEFAULTEXTENSION = ".pjo" else: DEFAULTEXTENSION = ".pso" FILETYPES = ((PACKAGE+" files", "*"+DEFAULTEXTENSION), ("All files", "*")) def mOpen(self, *event): if self._cancelDrag(): return filename = self.game.filename if filename: idir, ifile = os.path.split(os.path.normpath(filename)) else: idir, ifile = "", "" if not idir: idir = self.app.dn.savegames d = tkFileDialog.Open() filename = d.show(filetypes=self.FILETYPES, defaultextension=self.DEFAULTEXTENSION, initialdir=idir, initialfile=ifile) if filename: filename = os.path.normpath(filename) ##filename = os.path.normcase(filename) if os.path.isfile(filename): self.game.loadGame(filename) def mSaveAs(self, *event): if self._cancelDrag(): return if not self.menustate.save_as: return filename = self.game.filename if not filename: filename = self.app.getGameSaveName(self.game.id) if os.name == "posix": filename = filename + "-" + self.game.getGameNumber(format=0) else: filename = filename + "-01" filename = filename + self.DEFAULTEXTENSION idir, ifile = os.path.split(os.path.normpath(filename)) if not idir: idir = self.app.dn.savegames ##print self.game.filename, ifile d = tkFileDialog.SaveAs() filename = d.show(filetypes=self.FILETYPES, defaultextension=self.DEFAULTEXTENSION, initialdir=idir, initialfile=ifile) if filename: filename = os.path.normpath(filename) ##filename = os.path.normcase(filename) self.game.saveGame(filename) self.updateMenus() def mSelectCardsetDialog(self, *event): if self._cancelDrag(): return ##strings, default = ("OK", "Load", "Cancel"), 0 strings, default = (None, "Load", "Cancel"), 1 if PACKAGE == "PySol": if os.name == "posix": strings, default = (None, "Load", "Cancel", "Info...",), 1 pass t = CARDSET key = self.app.nextgame.cardset.index d = SelectCardsetDialogWithPreview(self.top, title="Select "+t, app=self.app, manager=self.app.cardset_manager, key=key, strings=strings, default=default) cs = self.app.cardset_manager.get(d.key) if cs is None or d.key == self.app.cardset.index: return if d.status == 0 and d.button in (0, 1) and d.key >= 0: self.app.nextgame.cardset = cs if d.button == 1: self.game.endGame(bookmark=1) self.game.quitGame(bookmark=1) def _mOptCardback(self, index): if self._cancelDrag(): return cs = self.app.cardset old_index = cs.backindex cs.updateCardback(backindex=index) if cs.backindex == old_index: return self.app.updateCardset(self.game.id) for card in self.game.cards: image = self.app.images.getBack(card.deck, card.suit, card.rank) card.updateCardBackground(image=image) self.app.canvas.update_idletasks() self.tkopt.cardback.set(cs.backindex) def mOptCardback(self, *event): self._mOptCardback(self.tkopt.cardback.get()) def mOptChangeCardback(self, *event): self._mOptCardback(self.app.cardset.backindex + 1) def _mOptTableTile(self, i): if self.app.setTile(i): self.tkopt.tabletile.set(i) def _mOptTableColor(self, color): tile = self.app.tabletile_manager.get(0) tile.color = color if self.app.setTile(0): self.tkopt.tabletile.set(0) def mOptTableTile(self, *event): if self._cancelDrag(): return self._mOptTableTile(self.tkopt.tabletile.get()) def mOptChangeTableTile(self, *event): if self._cancelDrag(): return n = self.app.tabletile_manager.len() if n >= 2: i = (self.tkopt.tabletile.get() + 1) % n self._mOptTableTile(i) def mSelectTileDialog(self, *event): if self._cancelDrag(): return key = self.app.tabletile_index if key <= 0: key = string.lower(self.app.opt.tablecolor) d = SelectTileDialogWithPreview(self.top, title="Select table background", app=self.app, manager=self.app.tabletile_manager, key=key) if d.status == 0 and d.button in (0, 1): if type(d.key) is types.StringType: self._mOptTableColor(d.key) elif d.key > 0 and d.key != self.app.tabletile_index: self._mOptTableTile(d.key) def mOptTableColor(self, *event): if self._cancelDrag(): return c = tkColorChooser.askcolor(initialcolor=self.app.opt.tablecolor, title="Select table color") if c and c[1]: self._mOptTableColor(c[1]) def mOptToolbar(self, *event): if self._cancelDrag(): return self.setToolbarSide(self.tkopt.toolbar.get()) def mOptToolbarSize(self, *event): if self._cancelDrag(): return self.setToolbarSize(self.tkopt.toolbar_size.get()) def mOptToolbarRelief(self, *event): if self._cancelDrag(): return self.setToolbarRelief(self.tkopt.toolbar_relief.get()) def mOptStatusbar(self, *event): if self._cancelDrag(): return if not self.app.statusbar: return side = self.tkopt.statusbar.get() self.app.opt.statusbar = side if self.app.statusbar.show(side): self.top.update_idletasks() # # toolbar support # def setToolbarSide(self, side): if self._cancelDrag(): return self.app.opt.toolbar = side self.tkopt.toolbar.set(side) # update radiobutton if self.app.toolbar.show(side): self.top.update_idletasks() def setToolbarSize(self, size): if self._cancelDrag(): return self.app.opt.toolbar_size = size self.tkopt.toolbar_size.set(size) # update radiobutton dir = self.app.getToolbarImagesDir(size) if self.app.toolbar.updateImages(dir, size): self.game.updateStatus(player=self.app.opt.player) self.top.update_idletasks() def setToolbarRelief(self, relief): if self._cancelDrag(): return self.app.opt.toolbar_relief = relief self.tkopt.toolbar_relief.set(relief) # update radiobutton ### FIXME self.top.update_idletasks()