From 1ec8cc8b27c51c1dc6851c0932162ca2420084bc Mon Sep 17 00:00:00 2001 From: Shlomi Fish Date: Sun, 16 Apr 2017 20:46:15 +0300 Subject: [PATCH] flake8 checked g*.py. --- pysollib/game.py | 866 +++++++++++++++++++++------------------- pysollib/gamedb.py | 408 ++++++++++--------- tests/style/py-flake8.t | 2 +- 3 files changed, 693 insertions(+), 583 deletions(-) diff --git a/pysollib/game.py b/pysollib/game.py index 91d45655..3252a4fe 100644 --- a/pysollib/game.py +++ b/pysollib/game.py @@ -1,33 +1,34 @@ -#!/usr/bin/env python +# !/usr/bin/env python # -*- mode: python; coding: utf-8; -*- -##---------------------------------------------------------------------------## -## -## Copyright (C) 1998-2003 Markus Franz Xaver Johannes Oberhumer -## Copyright (C) 2003 Mt. Hood Playing Card Co. -## Copyright (C) 2005-2009 Skomoroh -## -## 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 . -## -##---------------------------------------------------------------------------## +# --------------------------------------------------------------------------- +# +# Copyright (C) 1998-2003 Markus Franz Xaver Johannes Oberhumer +# Copyright (C) 2003 Mt. Hood Playing Card Co. +# Copyright (C) 2005-2009 Skomoroh +# +# 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 . +# +# --------------------------------------------------------------------------- # imports +import sys import time import math import traceback -from pysollib.mygettext import _, n_ +from pysollib.mygettext import _ from gettext import ungettext from cStringIO import StringIO @@ -42,7 +43,8 @@ from pysollib.settings import PACKAGE, TITLE, TOOLKIT, TOP_TITLE from pysollib.settings import VERSION, VERSION_TUPLE from pysollib.settings import DEBUG from pysollib.gamedb import GI -from pysollib.pysolrandom import PysolRandom, LCRandom31, constructRandom, random__long2str, random__str2long +from pysollib.pysolrandom import PysolRandom, LCRandom31, constructRandom, \ + random__long2str, random__str2long from pysollib.pysoltk import EVENT_HANDLED, EVENT_PROPAGATE from pysollib.pysoltk import CURSOR_WATCH from pysollib.pysoltk import bind, wm_map @@ -59,6 +61,11 @@ from pysollib.move import ASingleCardMove from pysollib.hint import DefaultHint from pysollib.help import help_about +if sys.version_info > (3,): + basestring = str + long = int + xrange = range + PLAY_TIME_TIMEOUT = 200 # ************************************************************************ @@ -70,12 +77,13 @@ PLAY_TIME_TIMEOUT = 200 # * hints/demo # ************************************************************************ + class Game: # for self.gstats.updated - U_PLAY = 0 - U_WON = -2 - U_LOST = -3 - U_PERFECT = -4 + U_PLAY = 0 + U_WON = -2 + U_LOST = -3 + U_PERFECT = -4 # for self.moves.state S_INIT = 0x00 @@ -90,7 +98,6 @@ class Game: # the format for a saved game changed (see also canLoadGame()) GAME_VERSION = 1 - # # game construction # @@ -117,44 +124,46 @@ class Game: self.demo_logo = None self.pause_logo = None self.s = Struct( # stacks - talon = None, - waste = None, - foundations = [], - rows = [], - reserves = [], - internals = [], + talon=None, + waste=None, + foundations=[], + rows=[], + reserves=[], + internals=[], ) self.sg = Struct( # stack-groups - openstacks = [], # for getClosestStack(): only on these stacks the player can place a card - talonstacks = [], # for Hint - dropstacks = [], # for Hint & getAutoStacks() - reservestacks = [], # for Hint -## hint = Struct(), # extra info for class Hint - hp_stacks = [], # for getHightlightPilesStacks() + openstacks=[], # for getClosestStack(): only on + # these stacks the player can place a card + talonstacks=[], # for Hint + dropstacks=[], # for Hint & getAutoStacks() + reservestacks=[], # for Hint + # hint=Struct(), # extra info for class Hint + hp_stacks=[], # for getHightlightPilesStacks() ) self.regions = Struct( # for getClosestStack() # set by optimizeRegions(): - info = [], # list of tuples(stacks, rect) - remaining = [], # list of stacks in no region + info=[], # list of tuples(stacks, rect) + remaining=[], # list of stacks in no region # - data = [], # raw data - init_info = [], # init info (at the start) + data=[], # raw data + init_info=[], # init info (at the start) ) - self.init_size = (0,0) + self.init_size = (0, 0) self.event_handled = False # if click event handled by Stack (???) self.reset() # main constructor def create(self, app): - #print 'Game.create' + # print 'Game.create' old_busy = self.busy self.__createCommon(app) self.setCursor(cursor=CURSOR_WATCH) - #print 'gameid:', self.id + # print 'gameid:', self.id self.top.wm_title(TITLE + " - " + self.getTitleName()) self.top.wm_iconname(TITLE + " - " + self.getTitleName()) # create the game - if self.app.intro.progress: self.app.intro.progress.update(step=1) + if self.app.intro.progress: + self.app.intro.progress.update(step=1) self.createGame() # set some defaults self.sg.openstacks = [s for s in self.sg.openstacks @@ -188,13 +197,14 @@ class Game: if not self.cards: self.cards = self.createCards(progress=self.app.intro.progress) self.initBindings() - ##self.top.bind('', self.top._sleepEvent) - ##self.top.bind('<3>', self.top._sleepEvent) + # self.top.bind('', self.top._sleepEvent) + # self.top.bind('<3>', self.top._sleepEvent) # update display properties self.canvas.busy = True # geometry - if not USE_PIL and self.app.opt.save_games_geometry and \ - self.id in self.app.opt.games_geometry: + mycond = (not USE_PIL and self.app.opt.save_games_geometry and + self.id in self.app.opt.games_geometry) + if mycond: # restore game geometry w, h = self.app.opt.games_geometry[self.id] self.canvas.config(width=w, height=h) @@ -203,9 +213,9 @@ class Game: w, h = self.app.opt.game_geometry self.canvas.setInitialSize(w, h, margins=False, scrollregion=False) - ## self.canvas.config(width=w, height=h) - ## dx, dy = self.canvas.xmargin, self.canvas.ymargin - ## self.canvas.config(scrollregion=(-dx, -dy, dx, dy)) + # self.canvas.config(width=w, height=h) + # dx, dy = self.canvas.xmargin, self.canvas.ymargin + # self.canvas.config(scrollregion=(-dx, -dy, dx, dy)) else: w = int(round(self.width * self.app.opt.scale_x)) h = int(round(self.height * self.app.opt.scale_y)) @@ -245,7 +255,6 @@ class Game: self.Stuck_Class = hint_class(self, 0) self.busy = old_busy - def _checkGame(self): class_name = self.__class__.__name__ if self.s.foundations: @@ -254,7 +263,8 @@ class Game: ncards += stack.cap.max_cards if ncards != self.gameinfo.ncards: print_err('invalid sum of foundations.max_cards: ' - '%s: %s %s' % (class_name, ncards, self.gameinfo.ncards), + '%s: %s %s' % + (class_name, ncards, self.gameinfo.ncards), 2) if self.s.rows: from pysollib.stack import AC_RowStack, UD_AC_RowStack, \ @@ -283,26 +293,23 @@ class Game: print_err('shallHighlightMatch is not valid (wrap): ' ' %s, %s' % (class_name, r.__class__), 2) break - if self.s.talon.max_rounds > 1 and \ - self.s.talon.texts.rounds is None: + if self.s.talon.max_rounds > 1 and self.s.talon.texts.rounds is None: print_err('max_rounds > 1, but talon.texts.rounds is None: ' '%s' % class_name, 2) - elif self.s.talon.max_rounds <= 1 and \ - self.s.talon.texts.rounds is not None: + elif (self.s.talon.max_rounds <= 1 and + self.s.talon.texts.rounds is not None): print_err('max_rounds <= 1, but talon.texts.rounds is not None: ' '%s' % class_name, 2) - def initBindings(self): # note: a Game is only allowed to bind self.canvas and not to self.top - ##bind(self.canvas, "", self.undoHandler) + # bind(self.canvas, "", self.undoHandler) bind(self.canvas, "<1>", self.undoHandler) bind(self.canvas, "<2>", self.dropHandler) bind(self.canvas, "<3>", self.redoHandler) bind(self.canvas, '', self._unmapHandler) bind(self.canvas, '', self._configureHandler, add=True) - def __createCommon(self, app): self.busy = 1 self.app = app @@ -310,38 +317,38 @@ class Game: self.canvas = app.canvas self.filename = "" self.drag = Struct( - event = None, # current event - timer = None, # current event timer - start_x = 0, # X coord of initial drag event - start_y = 0, # Y coord of initial drag event - stack = None, # - cards = [], # - index = -1, # - shadows = [], # list of canvas images - shade_stack = None, # stack currently shaded - shade_img = None, # canvas image - canshade_stacks = [], # list of stacks already tested - noshade_stacks = [], # for this drag + event=None, # current event + timer=None, # current event timer + start_x=0, # X coord of initial drag event + start_y=0, # Y coord of initial drag event + stack=None, # + cards=[], # + index=-1, # + shadows=[], # list of canvas images + shade_stack=None, # stack currently shaded + shade_img=None, # canvas image + canshade_stacks=[], # list of stacks already tested + noshade_stacks=[], # for this drag ) if self.gstats.start_player is None: self.gstats.start_player = self.app.opt.player # optional MfxCanvasText items self.texts = Struct( - info = None, # misc info text - help = None, # a static help text - misc = None, # - score = None, # for displaying the score - base_rank = None, # for displaying the base_rank - list = [], # list of texts (if we use many text) + info=None, # misc info text + help=None, # a static help text + misc=None, # + score=None, # for displaying the score + base_rank=None, # for displaying the base_rank + list=[], # list of texts (if we use many text) ) # initial position of the texts self.init_texts = Struct( - info = None, # misc info text - help = None, # a static help text - misc = None, # - score = None, # for displaying the score - base_rank = None, # for displaying the base_rank - list = [], + info=None, # misc info text + help=None, # a static help text + misc=None, # + score=None, # for displaying the score + base_rank=None, # for displaying the base_rank + list=[], ) def createPreview(self, app): @@ -381,70 +388,73 @@ class Game: self.demo = None self.solver = None self.hints = Struct( - list = None, # list of hints for the current move - index = -1, - level = -1, + list=None, # list of hints for the current move + index=-1, + level=-1, ) self.saveinfo = Struct( # needed for saving a game - stack_caps = [], + stack_caps=[], ) self.loadinfo = Struct( # used when loading a game - stacks = None, - talon_round = 1, - ncards = 0, + stacks=None, + talon_round=1, + ncards=0, ) self.snapshots = [] self.failed_snapshots = [] # local statistics are reset on each game restart self.stats = Struct( - hints = 0, # number of hints consumed - highlight_piles = 0, # number of highlight piles consumed - highlight_cards = 0, # number of highlight matching cards consumed - highlight_samerank = 0, # number of highlight same rank consumed - undo_moves = 0, # number of undos - redo_moves = 0, # number of redos - total_moves = 0, # number of total moves in this game - player_moves = 0, # number of moves - demo_moves = 0, # number of moves while in demo mode - autoplay_moves = 0, # number of moves - quickplay_moves = 0, # number of quickplay moves - goto_bookmark_moves = 0, # number of goto bookmark - shuffle_moves = 0, # number of shuffles (Mahjongg) - demo_updated = 0, # did this game already update the demo stats ? - update_time = time.time(), # for updateTime() - elapsed_time = 0.0, - pause_start_time = 0.0, + hints=0, # number of hints consumed + highlight_piles=0, # number of highlight piles consumed + # number of highlight matching cards consumed + highlight_cards=0, + highlight_samerank=0, # number of highlight same rank consumed + undo_moves=0, # number of undos + redo_moves=0, # number of redos + total_moves=0, # number of total moves in this game + player_moves=0, # number of moves + demo_moves=0, # number of moves while in demo mode + autoplay_moves=0, # number of moves + quickplay_moves=0, # number of quickplay moves + goto_bookmark_moves=0, # number of goto bookmark + shuffle_moves=0, # number of shuffles (Mahjongg) + # did this game already update the demo stats ? + demo_updated=0, + update_time=time.time(), # for updateTime() + elapsed_time=0.0, + pause_start_time=0.0, ) self.startMoves() if restart: return # global statistics survive a game restart self.gstats = Struct( - holded = 0, # is this a holded game - loaded = 0, # number of times this game was loaded - saved = 0, # number of times this game was saved - restarted = 0, # number of times this game was restarted - goto_bookmark_moves = 0, # number of goto bookmark - updated = self.U_PLAY, # did this game already update the player stats ? - start_time = time.time(), # game start time - total_elapsed_time = 0.0, - start_player = None, + holded=0, # is this a holded game + loaded=0, # number of times this game was loaded + saved=0, # number of times this game was saved + restarted=0, # number of times this game was restarted + goto_bookmark_moves=0, # number of goto bookmark + # did this game already update the player stats ? + updated=self.U_PLAY, + start_time=time.time(), # game start time + total_elapsed_time=0.0, + start_player=None, ) # global saveinfo survives a game restart self.gsaveinfo = Struct( - bookmarks = {}, - comment = "", + bookmarks={}, + comment="", ) # some vars for win animation self.win_animation = Struct( - timer = None, - images = [], - tk_images = [], # saved tk images - saved_images = {}, # saved resampled images - canvas_images = [], # ids of canvas images - frame_num = 0, # number of the current frame - width = 0, - height = 0, + timer=None, + images=[], + tk_images=[], # saved tk images + saved_images={}, # saved resampled images + canvas_images=[], # ids of canvas images + frame_num=0, # number of the current frame + width=0, + height=0, ) def getTitleName(self): @@ -452,7 +462,8 @@ class Game: def getGameNumber(self, format): s = self.random.getSeedAsStr() - if format: return "#" + s + if format: + return "# " + s return s # this is called from within createGame() @@ -464,10 +475,9 @@ class Game: def setCursor(self, cursor): if self.canvas: self.canvas.config(cursor=cursor) - ##self.canvas.update_idletasks() - #if self.app and self.app.toolbar: - # self.app.toolbar.setCursor(cursor=cursor) - + # self.canvas.update_idletasks() + # if self.app and self.app.toolbar: + # self.app.toolbar.setCursor(cursor=cursor) # # game creation @@ -475,7 +485,7 @@ class Game: # start a new name def newGame(self, random=None, restart=0, autoplay=1): - #print 'Game.newGame' + # print 'Game.newGame' self.finished = False old_busy, self.busy = self.busy, 1 self.setCursor(cursor=CURSOR_WATCH) @@ -485,24 +495,27 @@ class Game: self.reset(restart=restart) self.resetGame() self.createRandom(random) - ##print self.random, self.random.__dict__ + # print self.random, self.random.__dict__ self.shuffle() assert len(self.s.talon.cards) == self.gameinfo.ncards for stack in self.allstacks: stack.updateText() self.updateText() - self.updateStatus(player=self.app.opt.player, - gamenumber=self.getGameNumber(format=1), - moves=(0, 0), - stats=self.app.stats.getStats(self.app.opt.player, self.id), - stuck='') + self.updateStatus( + player=self.app.opt.player, + gamenumber=self.getGameNumber(format=1), + moves=(0, 0), + stats=self.app.stats.getStats( + self.app.opt.player, + self.id), + stuck='') reset_solver_dialog() # unhide toplevel when we use a progress bar if not self.preview: wm_map(self.top, maximized=self.app.opt.wm_maximized) self.top.busyUpdate() if TOOLKIT == 'gtk': - ## FIXME + # FIXME if self.top: self.top.update_idletasks() self.top.show_now() @@ -564,7 +577,7 @@ class Game: game.moves.state = old_state # 4) update settings for stack_id, cap in self.saveinfo.stack_caps: - ##print stack_id, cap + # print stack_id, cap self.allstacks[stack_id].cap.update(cap.__dict__) # 5) subclass settings self._restoreGameHook(game) @@ -572,10 +585,11 @@ class Game: for stack in self.allstacks: stack.updateText() self.updateText() - self.updateStatus(player=self.app.opt.player, - gamenumber=self.getGameNumber(format=1), - moves=(self.moves.index, self.stats.total_moves), - stats=self.app.stats.getStats(self.app.opt.player, self.id)) + self.updateStatus( + player=self.app.opt.player, + gamenumber=self.getGameNumber(format=1), + moves=(self.moves.index, self.stats.total_moves), + stats=self.app.stats.getStats(self.app.opt.player, self.id)) if not self.preview: self.updateMenus() wm_map(self.top, maximized=self.app.opt.wm_maximized) @@ -583,11 +597,12 @@ class Game: self.stats.update_time = time.time() self.busy = old_busy # - ##self._configureHandler() # reallocateCards - after(self.top, 200, self._configureHandler) # wait for canvas is mapped + # self._configureHandler() # reallocateCards + # wait for canvas is mapped + after(self.top, 200, self._configureHandler) # if TOOLKIT == 'gtk': - ## FIXME + # FIXME if self.top: self.top.update_idletasks() self.top.show_now() @@ -606,11 +621,11 @@ class Game: self.busy = old_busy def resetGame(self): - #print 'Game.resetGame' + # print 'Game.resetGame' self.hints.list = None self.s.talon.removeAllCards() for stack in self.allstacks: - ##print stack + # print stack stack.resetGame() if TOOLKIT == 'gtk': # FIXME (pyramid like games) @@ -675,8 +690,10 @@ class Game: if self.shallUpdateBalance(): b = self.getGameBalance() if b: - stats.total_balance[self.id] = stats.total_balance.get(self.id, 0) + b - stats.session_balance[self.id] = stats.session_balance.get(self.id, 0) + b + stats.total_balance[self.id] = \ + stats.total_balance.get(self.id, 0) + b + stats.session_balance[self.id] = \ + stats.session_balance.get(self.id, 0) + b stats.gameid_balance = stats.gameid_balance + b # restart the current game @@ -692,13 +709,15 @@ class Game: vw = self.canvas.winfo_width() vh = self.canvas.winfo_height() else: - # we have no a real size of canvas (winfo_width / winfo_reqwidth) + # we have no a real size of canvas + # (winfo_width / winfo_reqwidth) # so we use a saved size vw, vh = self.app.opt.game_geometry if not vw: # first run of the game return 1, 1 - iw, ih = self.init_size # requested size of canvas (createGame -> setSize) + # requested size of canvas (createGame -> setSize) + iw, ih = self.init_size # calculate factor of resizing xf = float(vw)/iw yf = float(vh)/ih @@ -714,19 +733,19 @@ class Game: return xf, yf def resizeGame(self): - #if self.busy: - # return + # if self.busy: + # return if not USE_PIL: return self.deleteStackDesc() xf, yf = self.resizeImages() - #print 'resizeGame', xf, yf + # print 'resizeGame', xf, yf # stacks for stack in self.allstacks: x0, y0 = stack.init_coord x, y = int(round(x0*xf)), int(round(y0*yf)) - #if x == stack.x and y == stack.y: - # continue + # if x == stack.x and y == stack.y: + # continue stack.resize(xf, yf) stack.updatePositions() # regions @@ -741,7 +760,8 @@ class Game: init_coord = getattr(self.init_texts, t) if init_coord: item = getattr(self.texts, t) - x, y = int(round(init_coord[0]*xf)), int(round(init_coord[1]*yf)) + x, y = int(round(init_coord[0]*xf)), \ + int(round(init_coord[1]*yf)) self.canvas.coords(item, x, y) for i in range(len(self.texts.list)): init_coord = self.init_texts.list[i] @@ -749,8 +769,8 @@ class Game: x, y = int(round(init_coord[0]*xf)), int(round(init_coord[1]*yf)) self.canvas.coords(item, x, y) # - #self.canvas.update() - #self.canvas.update_idletasks() + # self.canvas.update() + # self.canvas.update_idletasks() def createRandom(self, random): if random is None: @@ -758,15 +778,17 @@ class Game: state = self.random.getstate() self.app.gamerandom.setstate(state) # we want at least 17 digits - seed = self.app.gamerandom.randrange(10000000000000000L, - PysolRandom.MAX_SEED) + seed = self.app.gamerandom.randrange( + long('10000000000000000'), + PysolRandom.MAX_SEED + ) self.random = PysolRandom(seed) self.random.origin = self.random.ORIGIN_RANDOM else: self.random = random self.random.reset() - ##print 'createRandom:', self.random - ##print "createRandom: origin =", self.random.origin + # print 'createRandom:', self.random + # print "createRandom: origin =", self.random.origin def enterState(self, state): old_state = self.moves.state @@ -805,18 +827,16 @@ class Game: sg[s] = [s.id] sg = sg.values() self.sn_groups = sg - ##print sg - + # print sg def updateSnapshots(self): sn = self.getSnapshot() if sn in self.snapshots: - ##self.updateStatus(snapshot=True) + # self.updateStatus(snapshot=True) pass else: self.snapshots.append(sn) - ##self.updateStatus(snapshot=False) - + # self.updateStatus(snapshot=False) # # card creation & shuffling @@ -839,7 +859,8 @@ class Game: continue cards.append(card) id = id + 1 - if progress: progress.update(step=pstep) + if progress: + progress.update(step=pstep) trump_suit = len(gi.suits) for rank in gi.trumps: card = self._createCard(id, deck, trump_suit, rank, x=x, y=y) @@ -847,8 +868,10 @@ class Game: continue cards.append(card) id = id + 1 - if progress: progress.update(step=pstep) - if progress: progress.update(percent=100) + if progress: + progress.update(step=pstep) + if progress: + progress.update(percent=100) assert len(cards) == gi.ncards return cards @@ -924,7 +947,6 @@ class Game: scards = [item[2] for item in sitems] return cards, scards - # # menu support # @@ -932,7 +954,8 @@ class Game: def _finishDrag(self): if self.demo: self.stopDemo() - if self.busy: return 1 + if self.busy: + return 1 if self.drag.stack: self.drag.stack.finishDrag() return 0 @@ -945,7 +968,8 @@ class Game: self.doPause() self.interruptSleep() self.deleteStackDesc() - if self.busy: return 1 + if self.busy: + return 1 if self.drag.stack: self.drag.stack.cancelDrag() return 0 @@ -958,7 +982,6 @@ class Game: if not self.preview: self.app.menubar.disableMenus() - # # UI & graphics support # @@ -1013,46 +1036,56 @@ class Game: for k, v in kw.items(): if k == "gamenumber": if v is None: - if sb: sb.updateText(gamenumber="") - #self.top.wm_title("%s - %s" % (TITLE, self.getTitleName())) + if sb: + sb.updateText(gamenumber="") + # self.top.wm_title("%s - %s" + # % (TITLE, self.getTitleName())) continue if isinstance(v, basestring): - if sb: sb.updateText(gamenumber=v) - #self.top.wm_title("%s - %s %s" % (TITLE, - # self.getTitleName(), v)) + if sb: + sb.updateText(gamenumber=v) + # self.top.wm_title("%s - %s %s" % (TITLE, + # self.getTitleName(), v)) continue if k == "info": - ##print 'updateStatus info:', v + # print 'updateStatus info:', v if v is None: - if sb: sb.updateText(info="") + if sb: + sb.updateText(info="") continue if isinstance(v, str): - if sb: sb.updateText(info=v) + if sb: + sb.updateText(info=v) continue if k == "moves": if v is None: - ##if tb: tb.updateText(moves="Moves\n") - if sb: sb.updateText(moves="") + # if tb: tb.updateText(moves="Moves\n") + if sb: + sb.updateText(moves="") continue if isinstance(v, tuple): - ##if tb: tb.updateText(moves="Moves\n%d/%d" % v) - if sb: sb.updateText(moves="%d/%d" % v) + # if tb: tb.updateText(moves="Moves\n%d/%d" % v) + if sb: + sb.updateText(moves="%d/%d" % v) continue if isinstance(v, int): - ##if tb: tb.updateText(moves="Moves\n%d" % v) - if sb: sb.updateText(moves="%d" % v) + # if tb: tb.updateText(moves="Moves\n%d" % v) + if sb: + sb.updateText(moves="%d" % v) continue if isinstance(v, str): - ##if tb: tb.updateText(moves=v) - if sb: sb.updateText(moves=v) + # if tb: tb.updateText(moves=v) + if sb: + sb.updateText(moves=v) continue if k == "player": if v is None: - if tb: tb.updateText(player=_("Player\n")) + if tb: + tb.updateText(player=_("Player\n")) continue if isinstance(v, basestring): if tb: - #if self.app.opt.toolbar_size: + # if self.app.opt.toolbar_size: if self.app.toolbar.getSize(): tb.updateText(player=_("Player\n") + v) else: @@ -1060,20 +1093,25 @@ class Game: continue if k == "stats": if v is None: - if sb: sb.updateText(stats="") + if sb: + sb.updateText(stats="") continue if isinstance(v, tuple): t = "%d: %d/%d" % (v[0]+v[1], v[0], v[1]) - if sb: sb.updateText(stats=t) + if sb: + sb.updateText(stats=t) continue if k == "time": if v is None: - if sb: sb.updateText(time='') + if sb: + sb.updateText(time='') if isinstance(v, basestring): - if sb: sb.updateText(time=v) + if sb: + sb.updateText(time=v) continue if k == 'stuck': - if sb: sb.updateText(stuck=v) + if sb: + sb.updateText(stuck=v) continue raise AttributeError(k) @@ -1083,13 +1121,14 @@ class Game: self.app.menubar.mPause() _resizeHandlerID = None + def _resizeHandler(self): - #print '_resizeHandler' + # print '_resizeHandler' self._resizeHandlerID = None self.resizeGame() def _configureHandler(self, event=None): - #print 'configureHandler' + # print 'configureHandler' if not USE_PIL: return if not self.app: @@ -1109,12 +1148,15 @@ class Game: # def playSample(self, name, priority=0, loop=0): - ##print "Game.playSample:", name, priority, loop + # print "Game.playSample:", name, priority, loop if name in self.app.opt.sound_samples and \ not self.app.opt.sound_samples[name]: return 0 if self.app.audio: - return self.app.audio.playSample(name, priority=priority, loop=loop) + return self.app.audio.playSample( + name, + priority=priority, + loop=loop) return 0 def stopSamples(self): @@ -1129,7 +1171,8 @@ class Game: a = self.app.opt.animations if a and not self.preview: self.canvas.update_idletasks() - if self.app.audio and self.app.opt.sound and self.app.opt.sound_samples['deal']: + if self.app.audio and self.app.opt.sound \ + and self.app.opt.sound_samples['deal']: if a in (1, 2, 3, 10): self.playSample("deal01", priority=100, loop=loop) elif a == 4: @@ -1137,7 +1180,6 @@ class Game: elif a == 5: self.playSample("deal08", priority=100, loop=loop) - # # misc. methods # @@ -1148,8 +1190,10 @@ class Game: if confirm < 0: confirm = self.app.opt.confirm if confirm: - if not title: title = TITLE - if not text: text = _("Discard current game ?") + if not title: + title = TITLE + if not text: + text = _("Discard current game ?") self.playSample("areyousure") d = MfxMessageDialog(self.top, title=title, text=text, bitmap="question", @@ -1160,21 +1204,21 @@ class Game: def notYetImplemented(self): # don't used - d = MfxMessageDialog(self.top, title="Not yet implemented", - text="This function is\nnot yet implemented.", - bitmap="error") + MfxMessageDialog(self.top, title="Not yet implemented", + text="This function is\nnot yet implemented.", + bitmap="error") # main animation method def animatedMoveTo(self, from_stack, to_stack, cards, x, y, tkraise=1, frames=-1, shadow=-1): # available values of app.opt.animations: - # 0 - without animations - # 1 - very fast (without timer) - # 2 - fast (default) - # 3 - medium (2/3 of fast speed) - # 4 - slow (1/4 of fast speed) - # 5 - very slow (1/8 of fast speed) - # 10 - used internally in game preview + # 0 - without animations + # 1 - very fast (without timer) + # 2 - fast (default) + # 3 - medium (2/3 of fast speed) + # 4 - slow (1/4 of fast speed) + # 5 - very slow (1/8 of fast speed) + # 10 - used internally in game preview if self.app.opt.animations == 0 or frames == 0: return # init timer - need a high resolution for this to work @@ -1210,13 +1254,15 @@ class Game: dx, dy = (x - c0.x) / float(frames), (y - c0.y) / float(frames) tx, ty = 0, 0 i = 1 - if clock: starttime = clock() + if clock: + starttime = clock() while i < frames: mx, my = int(round(dx * i)) - tx, int(round(dy * i)) - ty tx, ty = tx + mx, ty + my if i == 1 and shadow and from_stack: # create shadows in the first frame - sx, sy = self.app.images.SHADOW_XOFFSET, self.app.images.SHADOW_YOFFSET + sx, sy = self.app.images.SHADOW_XOFFSET, \ + self.app.images.SHADOW_YOFFSET shadows = from_stack.createShadows(cards, sx, sy) for s in shadows: s.move(mx, my) @@ -1229,15 +1275,16 @@ class Game: sleep = endtime - clock() if delay and sleep >= 0.005: # we're fast - delay - ##print "Delay frame", i, sleep + # print "Delay frame", i, sleep usleep(sleep) elif skip and sleep <= -0.75*SPF: # we're slow - skip 1 or 2 frames - ##print "Skip frame", i, sleep - step = step + 1 - if frames > 4 and sleep < -1.5*SPF: step = step + 1 - ##print i, step, mx, my; time.sleep(0.5) - i = i + step + # print "Skip frame", i, sleep + step += 1 + if frames > 4 and sleep < -1.5*SPF: + step += 1 + # print i, step, mx, my; time.sleep(0.5) + i += step # last frame: delete shadows, move card to final position for s in shadows: s.delete() @@ -1246,7 +1293,6 @@ class Game: card.moveBy(dx, dy) self.canvas.update_idletasks() - def doAnimatedFlipAndMove(self, from_stack, to_stack=None, frames=-1): if self.app.opt.animations == 0 or frames == 0: return False @@ -1269,13 +1315,13 @@ class Game: # SPF = 0.1/8 # animation speed - seconds per frame frames = 4.0 # num frames for each step - if self.app.opt.animations == 3: # medium + if self.app.opt.animations == 3: # medium SPF = 0.1/8 frames = 7.0 - elif self.app.opt.animations == 4: # slow + elif self.app.opt.animations == 4: # slow SPF = 0.1/8 frames = 12.0 - elif self.app.opt.animations == 5: # very slow + elif self.app.opt.animations == 5: # very slow SPF = 0.1/8 frames = 24.0 @@ -1290,14 +1336,14 @@ class Game: if dest_x == 0 and dest_y == 0: # flip - #ascent_dx, ascent_dy = 0, self.app.images.SHADOW_YOFFSET/frames + # ascent_dx, ascent_dy = 0, self.app.images.SHADOW_YOFFSET/frames ascent_dx, ascent_dy = 0, h/10.0/frames min_size = w/10 shrink_dx = (w-min_size) / (frames-1) shrink_dy = 0 elif dest_y == 0: # move to left/right waste - #ascent_dx, ascent_dy = 0, self.app.images.SHADOW_YOFFSET/frames + # ascent_dx, ascent_dy = 0, self.app.images.SHADOW_YOFFSET/frames ascent_dx, ascent_dy = 0, h/10.0/frames min_size = w/10 shrink_dx = (w-min_size) / (frames-1) @@ -1345,13 +1391,13 @@ class Game: canvas.update_idletasks() nframe += 1 - t = (SPF-(uclock()-starttime))*1000 # milliseconds + t = (SPF-(uclock()-starttime))*1000 # milliseconds if t > 0: usleep(t/1000) -## else: -## nframe += 1 -## xpos += d_x -## ypos += d_y + # else: + # nframe += 1 + # xpos += d_x + # ypos += d_y # step 2 d_x = -shrink_dx/2+move_dx+ascent_dx @@ -1372,16 +1418,16 @@ class Game: canvas.update_idletasks() nframe += 1 - t = (SPF-(uclock()-starttime))*1000 # milliseconds + t = (SPF-(uclock()-starttime))*1000 # milliseconds if t > 0: usleep(t/1000) -## else: -## nframe += 1 -## xpos += d_x -## ypos += d_y + # else: + # nframe += 1 + # xpos += d_x + # ypos += d_y card.moveTo(x1, y1) - #canvas.update_idletasks() + # canvas.update_idletasks() return True def animatedFlip(self, stack): @@ -1394,14 +1440,13 @@ class Game: return False return self.doAnimatedFlipAndMove(from_stack, to_stack, frames) - def winAnimationEvent(self): # based on code from pygtk-demo FRAME_DELAY = 80 CYCLE_LEN = 60 starttime = uclock() images = self.win_animation.images - saved_images = self.win_animation.saved_images # cached images + saved_images = self.win_animation.saved_images # cached images canvas = self.canvas canvas.delete(*self.win_animation.canvas_images) self.win_animation.canvas_images = [] @@ -1422,7 +1467,7 @@ class Game: radius = min(xmid, ymid) / 2.0 f = float(self.win_animation.frame_num % CYCLE_LEN) / float(CYCLE_LEN) - r = radius +(radius / 3.0) * math.sin(f * 2.0 * math.pi) + r = radius + (radius / 3.0) * math.sin(f * 2.0 * math.pi) img_index = 0 for im in images: @@ -1463,7 +1508,8 @@ class Game: for id in raised_images: canvas.tag_raise(id) - self.win_animation.frame_num = (self.win_animation.frame_num+1) % CYCLE_LEN + self.win_animation.frame_num = \ + (self.win_animation.frame_num+1) % CYCLE_LEN self.win_animation.tk_images = tmp_tk_images canvas.update_idletasks() # loop @@ -1471,15 +1517,17 @@ class Game: if t > 0: self.win_animation.timer = after(canvas, t, self.winAnimationEvent) else: - self.win_animation.timer = after_idle(canvas, self.winAnimationEvent) + self.win_animation.timer = after_idle( + canvas, + self.winAnimationEvent) def stopWinAnimation(self): if self.win_animation.timer: - after_cancel(self.win_animation.timer) # stop loop + after_cancel(self.win_animation.timer) # stop loop self.win_animation.timer = None self.canvas.delete(*self.win_animation.canvas_images) self.win_animation.canvas_images = [] - self.win_animation.tk_images = [] # delete all images + self.win_animation.tk_images = [] # delete all images self.saved_images = {} self.canvas.showAllItems() return True @@ -1488,8 +1536,8 @@ class Game: def winAnimation(self, perfect=0): if self.preview: return - #if not self.app.opt.animations: - # return + # if not self.app.opt.animations: + # return if not self.app.opt.win_animation: return if TOOLKIT == 'gtk': @@ -1511,7 +1559,7 @@ class Game: self.win_animation.width = self.canvas.winfo_width() self.win_animation.height = self.canvas.winfo_height() # run win animation in background - ##after_idle(self.canvas, self.winAnimationEvent) + # after_idle(self.canvas, self.winAnimationEvent) after(self.canvas, 200, self.winAnimationEvent) return @@ -1524,7 +1572,7 @@ class Game: for s in self.allstacks: if s is not self.s.talon: for c in s.cards: - cards.append((c,s)) + cards.append((c, s)) if not cards: return self.setCursor(cursor=CURSOR_WATCH) @@ -1544,7 +1592,7 @@ class Game: c, s = self.app.miscrandom.choice(scards) if c not in acards: acards.append(c) - scards.remove((c,s)) + scards.remove((c, s)) if not scards: break # animate @@ -1557,7 +1605,8 @@ class Game: s.removeCard(c, update=0) # animation if c in acards or len(cards) <= 2: - self.animatedMoveTo(s, None, [c], w/2, h/2, tkraise=0, shadow=0) + self.animatedMoveTo( + s, None, [c], w/2, h/2, tkraise=0, shadow=0) self.animatedMoveTo(s, None, [c], sx, sy, tkraise=0, shadow=0) else: c.moveTo(sx, sy) @@ -1565,8 +1614,8 @@ class Game: self.app.opt.animations = old_a def sleep(self, seconds): -## if 0 and self.canvas: -## self.canvas.update_idletasks() + # if 0 and self.canvas: + # self.canvas.update_idletasks() if seconds > 0: if self.top: self.top.interruptSleep() @@ -1608,7 +1657,8 @@ class Game: def getClosestStack(self, card, dragstack): cx, cy = card.x, card.y for stacks, rect in self.regions.info: - if cx >= rect[0] and cx < rect[2] and cy >= rect[1] and cy < rect[3]: + if cx >= rect[0] and cx < rect[2] \ + and cy >= rect[1] and cy < rect[3]: return self._getClosestStack(cx, cy, stacks, dragstack) return self._getClosestStack(cx, cy, self.regions.remaining, dragstack) @@ -1627,10 +1677,10 @@ class Game: r = rect if USE_PIL: x, y = s.init_coord - #print 'setRegion:', x, y, r + # print 'setRegion:', x, y, r else: x, y = s.x, s.y - #print 'setRegion:', x, y, r + # print 'setRegion:', x, y, r assert r[0] <= x <= r[2] and r[1] <= y <= r[3] # verify that the stack is not already in another region # with the same priority @@ -1638,7 +1688,8 @@ class Game: if priority == d[0]: assert s not in d[2] # add to regions - self.regions.data.append((priority, -len(self.regions.data), tuple(stacks), tuple(rect))) + self.regions.data.append( + (priority, -len(self.regions.data), tuple(stacks), tuple(rect))) # as getClosestStack() is called within the mouse motion handler # event it is worth optimizing a little bit @@ -1662,12 +1713,11 @@ class Game: def getInvisibleCoords(self): # for InvisibleStack, etc - ##x, y = -500, -500 - len(game.allstacks) + # x, y = -500, -500 - len(game.allstacks) cardw, cardh = self.app.images.CARDW, self.app.images.CARDH x, y = cardw + self.canvas.xmargin, cardh + self.canvas.ymargin return -x-10, -y-10 - # # Game - subclass overridable actions - IMPORTANT FOR GAME LOGIC # @@ -1721,16 +1771,21 @@ class Game: # can we save outself ? def canSaveGame(self): return True + # can we load this game ? + def canLoadGame(self, version_tuple, game_version): return self.GAME_VERSION == game_version + # can we set a bookmark ? + def canSetBookmark(self): return self.canSaveGame() # can we undo/redo ? def canUndo(self): return True + def canRedo(self): return self.canUndo() @@ -1738,7 +1793,6 @@ class Game: def canShuffle(self): return False - # # Game - stats handlers # @@ -1765,10 +1819,10 @@ class Game: return won, 0, self.U_LOST if (self.stats.undo_moves == 0 and self.stats.goto_bookmark_moves == 0 and -### self.stats.quickplay_moves == 0 and + # self.stats.quickplay_moves == 0 and self.stats.highlight_piles == 0 and self.stats.highlight_cards == 0 and - self.stats.shuffle_moves == 0): + self.stats.shuffle_moves == 0): # perfect ! return won, 2, self.U_PERFECT return won, 1, self.U_WON @@ -1790,23 +1844,26 @@ class Game: # must update player stats self.gstats.updated = updated if self.app.opt.update_player_stats: - ret = self.app.stats.updateStats(self.app.opt.player, self, status) - self.updateStatus(stats=self.app.stats.getStats(self.app.opt.player, self.id)) + ret = self.app.stats.updateStats( + self.app.opt.player, self, status) + self.updateStatus( + stats=self.app.stats.getStats( + self.app.opt.player, self.id)) top_msg = '' if ret: if ret[0] and ret[1]: top_msg = _(''' You have reached -#%d in the %s of playing time -and #%d in the %s of moves.''') % (ret[0], TOP_TITLE, ret[1], TOP_TITLE) +# %d in the %s of playing time +and # %d in the %s of moves.''') % (ret[0], TOP_TITLE, ret[1], TOP_TITLE) elif ret[0]: # playing time top_msg = _(''' You have reached -#%d in the %s of playing time.''') % (ret[0], TOP_TITLE) +# %d in the %s of playing time.''') % (ret[0], TOP_TITLE) elif ret[1]: # moves top_msg = _(''' You have reached -#%d in the %s of moves.''') % (ret[1], TOP_TITLE) +# %d in the %s of moves.''') % (ret[1], TOP_TITLE) return top_msg elif not demo: # only update the session log @@ -1870,15 +1927,17 @@ Congratulations, you did it ! elif self.gstats.updated < 0: self.finished = True self.playSample("gamefinished", priority=1000) - d = MfxMessageDialog(self.top, title=_("Game finished"), bitmap="info", - text=_("\nGame finished\n"), - strings=(_("&New game"), None, _("&Cancel"))) + d = MfxMessageDialog( + self.top, title=_("Game finished"), bitmap="info", + text=_("\nGame finished\n"), + strings=(_("&New game"), None, _("&Cancel"))) else: self.finished = True self.playSample("gamelost", priority=1000) - d = MfxMessageDialog(self.top, title=_("Game finished"), bitmap="info", - text=_("\nGame finished, but not without my help...\n"), - strings=(_("&New game"), _("&Restart"), _("&Cancel"))) + d = MfxMessageDialog( + self.top, title=_("Game finished"), bitmap="info", + text=_("\nGame finished, but not without my help...\n"), + strings=(_("&New game"), _("&Restart"), _("&Cancel"))) self.updateMenus() if d.status == 0 and d.button == 0: # new game @@ -1889,7 +1948,6 @@ Congratulations, you did it ! self.restartGame() return 1 - # # Game - subclass overridable methods (but usually not) # @@ -1910,8 +1968,9 @@ Congratulations, you did it ! # determine the real number of player_moves def getPlayerMoves(self): player_moves = self.stats.player_moves -## if self.moves.index > 0 and self.stats.demo_moves == self.moves.index: -## player_moves = 0 + # if self.moves.index > 0 and + # self.stats.demo_moves == self.moves.index: + # player_moves = 0 return player_moves def updateTime(self): @@ -1931,7 +1990,6 @@ Congratulations, you did it ! t = int(self.stats.elapsed_time) return format_time(t) - # # Game - subclass overridable intelligence # @@ -1946,13 +2004,16 @@ Congratulations, you did it ! if self.demo: return 0 old_busy, self.busy = self.busy, 1 - if autofaceup < 0: autofaceup = self.app.opt.autofaceup - if autodrop < 0: autodrop = self.app.opt.autodrop - if autodeal < 0: autodeal = self.app.opt.autodeal + if autofaceup < 0: + autofaceup = self.app.opt.autofaceup + if autodrop < 0: + autodrop = self.app.opt.autodrop + if autodeal < 0: + autodeal = self.app.opt.autodeal moves = self.stats.total_moves n = self._autoPlay(autofaceup, autodrop, autodeal, sound=sound) self.finishMove() - self.stats.autoplay_moves = self.stats.autoplay_moves + (self.stats.total_moves - moves) + self.stats.autoplay_moves += (self.stats.total_moves - moves) self.busy = old_busy return n @@ -1967,7 +2028,7 @@ Congratulations, you did it ! if s.canFlipCard(): if sound: self.playSample("autoflip", priority=5) - #~s.flipMove() + # ~s.flipMove() s.flipMove(animation=True) done_something = 1 # each single flip is undo-able unless opt.autofaceup @@ -2006,12 +2067,12 @@ Congratulations, you did it ! def autoDrop(self, autofaceup=-1): old_a = self.app.opt.animations - if old_a == 3: # medium - self.app.opt.animations = 2 # fast + if old_a == 3: # medium + self.app.opt.animations = 2 # fast self.autoPlay(autofaceup=autofaceup, autodrop=1) self.app.opt.animations = old_a - ## for find_card_dialog + # for find_card_dialog def highlightCard(self, suit, rank): if not self.app: return None @@ -2024,14 +2085,14 @@ Congratulations, you did it ! info.append((s, c, c, col)) return self._highlightCards(info, 0) - ### highlight all moveable piles + # highlight all moveable piles def getHighlightPilesStacks(self): # default: dropstacks with min pile length = 2 if self.sg.hp_stacks: return ((self.sg.hp_stacks, 2),) return () - def _highlightCards(self, info, sleep=1.5, delta=(1,1,1,1)): + def _highlightCards(self, info, sleep=1.5, delta=(1, 1, 1, 1)): if not info: return 0 if self.pause: @@ -2065,7 +2126,7 @@ Congratulations, you did it ! if sx0 != 0 and sy0 == 0: # horizontal stack y2 += ch - if c2 is s.cards[-1]: # top card + if c2 is s.cards[-1]: # top card x2 += cw else: if sx0 > 0: @@ -2078,7 +2139,7 @@ Congratulations, you did it ! elif sx0 == 0 and sy0 != 0: # vertical stack x2 += cw - if c2 is s.cards[-1]: # top card + if c2 is s.cards[-1]: # top card y2 += ch else: if sy0 > 0: @@ -2092,7 +2153,7 @@ Congratulations, you did it ! x2 += cw y2 += ch tkraise = True - ##print c1, c2, x1, y1, x2, y2 + # print c1, c2, x1, y1, x2, y2 x1, x2 = x1-delta[0], x2+delta[1] y1, y2 = y1-delta[2], y2+delta[3] if TOOLKIT == 'tk': @@ -2221,7 +2282,6 @@ Congratulations, you did it ! and ((card1.rank + 1) % 13 == card2.rank or (card2.rank + 1) % 13 == card1.rank)) - # # quick-play # @@ -2229,7 +2289,7 @@ Congratulations, you did it ! def getQuickPlayScore(self, ncards, from_stack, to_stack): if to_stack in self.s.reserves: # if to_stack in reserves prefer empty stack - ##return 1000 - len(to_stack.cards) + # return 1000 - len(to_stack.cards) return 1000 - int(len(to_stack.cards) != 0) # prefer non-empty piles in to_stack return 1001 + int(len(to_stack.cards) != 0) @@ -2241,7 +2301,8 @@ Congratulations, you did it ! # for spider-type stacks if to_stack.cards: # check suit - same_suit = from_stack.cards[-ncards].suit == to_stack.cards[-1].suit + same_suit = (from_stack.cards[-ncards].suit == + to_stack.cards[-1].suit) return int(same_suit)+1002 return 1001 @@ -2275,7 +2336,6 @@ Congratulations, you did it ! def getGameBalance(self): return 0 - # # Hint - uses self.getHintClass() # @@ -2284,8 +2344,8 @@ Congratulations, you did it ! # this is the only method that actually uses class Hint def getHints(self, level, taken_hint=None): if level == 3: - #if self.solver is None: - # return None + # if self.solver is None: + # return None return self.solver.getHints(taken_hint) hint_class = self.getHintClass() if hint_class is None: @@ -2305,7 +2365,7 @@ Congratulations, you did it ! # compute all hints if self.hints.list is None: self.hints.list = self.getHints(level, taken_hint) - ###print self.hints.list + # print self.hints.list self.hints.index = 0 # get next hint from list if not self.hints.list: @@ -2334,25 +2394,27 @@ Congratulations, you did it ! assert 1 <= ncards <= len(from_stack.cards) if DEBUG: if not to_stack.acceptsCards( - from_stack, from_stack.cards[-ncards:]): - print '*fail accepts cards*', from_stack, to_stack, ncards + from_stack, from_stack.cards[-ncards:]): + print('*fail accepts cards*', from_stack, to_stack, ncards) if not from_stack.canMoveCards(from_stack.cards[-ncards:]): - print '*fail move cards*', from_stack, ncards - ##assert from_stack.canMoveCards(from_stack.cards[-ncards:]) # FIXME: Pyramid - assert to_stack.acceptsCards(from_stack, from_stack.cards[-ncards:]) + print('*fail move cards*', from_stack, ncards) + # assert from_stack.canMoveCards(from_stack.cards[-ncards:]) + # FIXME: Pyramid + assert to_stack.acceptsCards( + from_stack, from_stack.cards[-ncards:]) if sleep <= 0.0: return h info = (level == 1) or (level > 1 and DEBUG) if info and self.app.statusbar and self.app.opt.statusbar: - self.app.statusbar.configLabel("info", text=_("Score %6d") % (score), fg=text_color) + self.app.statusbar.configLabel( + "info", text=_("Score %6d") % (score), fg=text_color) else: info = 0 self.drawHintArrow(from_stack, to_stack, ncards, sleep) if info: - self.app.statusbar.configLabel("info", text="", fg="#000000") + self.app.statusbar.configLabel("info", text="", fg="# 000000") return h - def drawHintArrow(self, from_stack, to_stack, ncards, sleep): # compute position for arrow images = self.app.images @@ -2376,7 +2438,7 @@ Congratulations, you did it ! # draw the hint arrow = MfxCanvasLine(self.canvas, x1, y1, x2, y2, width=7, fill=self.app.opt.colors['hintarrow'], - arrow="last", arrowshape=(30,30,10)) + arrow="last", arrowshape=(30, 30, 10)) self.canvas.update_idletasks() # wait self.sleep(sleep) @@ -2385,7 +2447,6 @@ Congratulations, you did it ! arrow.delete() self.canvas.update_idletasks() - # # Demo - uses showHint() # @@ -2396,20 +2457,20 @@ Congratulations, you did it ! if not self.top: return self.demo = Struct( - level = level, - mixed = mixed, - sleep = self.app.opt.timeouts['demo'], - last_deal = [], - snapshots = [], - hint = None, - keypress = None, - start_demo_moves = self.stats.demo_moves, - info_text = None, + level=level, + mixed=mixed, + sleep=self.app.opt.timeouts['demo'], + last_deal=[], + snapshots=[], + hint=None, + keypress=None, + start_demo_moves=self.stats.demo_moves, + info_text=None, ) self.hints.list = None self.createDemoInfoText() self.createDemoLogo() - after_idle(self.top, self.demoEvent) # schedule first move + after_idle(self.top, self.demoEvent) # schedule first move # stop the demo def stopDemo(self, event=None): @@ -2425,7 +2486,7 @@ Congratulations, you did it ! # note: other events are allowed to stop self.demo at any time if not self.demo or self.demo.keypress: self.stopDemo() - #self.updateMenus() + # self.updateMenus() return finished = self.playOneDemoMove(self.demo) self.finishMove() @@ -2462,23 +2523,26 @@ Congratulations, you did it ! timeout=timeout) status = d.status else: - ##s = self.app.miscrandom.choice((_("&OK"), _("&OK"))) + # s = self.app.miscrandom.choice((_("&OK"), _("&OK"))) s = _("&OK") text = _("\nGame finished\n") if DEBUG: - text += "\nplayer_moves: %d\ndemo_moves: %d\n" % (self.stats.player_moves, self.stats.demo_moves) + text += "\nplayer_moves: %d\ndemo_moves: %d\n" % \ + (self.stats.player_moves, self.stats.demo_moves) d = MfxMessageDialog(self.top, title=TITLE+_(" Autopilot"), text=text, bitmap=bitmap, strings=(s,), padx=30, timeout=timeout) status = d.status elif finished: - ##self.stopPlayTimer() + # self.stopPlayTimer() if not self.top.winfo_ismapped(): status = 2 else: if player_moves == 0: self.playSample("autopilotlost", priority=1000) - s = self.app.miscrandom.choice((_("&Oh well"), _("&That's life"), _("&Hmm"))) # ??? accelerators + s = self.app.miscrandom.choice( + (_("&Oh well"), _("&That's life"), _("&Hmm"))) + # ??? accelerators d = MfxMessageDialog(self.top, title=TITLE+_(" Autopilot"), text=_("\nThis won't come out...\n"), bitmap=bitmap, strings=(s,), @@ -2491,7 +2555,7 @@ Congratulations, you did it ! if self.stats.demo_moves > self.demo.start_demo_moves: # we only increase the splash-screen counter if the last # demo actually made a move - self.app.demo_counter = self.app.demo_counter + 1 + self.app.demo_counter += 1 if self.app.demo_counter % 3 == 0: if self.top.winfo_ismapped(): status = help_about(self.app, timeout=10000) @@ -2502,7 +2566,7 @@ Congratulations, you did it ! if 1 and demo.mixed and DEBUG: # debug - advance game id to make sure we hit all games gl = self.app.gdb.getGamesIdSortedById() - ##gl = self.app.gdb.getGamesIdSortedByName() + # gl = self.app.gdb.getGamesIdSortedByName() gl = list(gl) index = (gl.index(self.id) + 1) % len(gl) id = gl[index] @@ -2532,7 +2596,7 @@ Congratulations, you did it ! # game not finished yet self.top.busyUpdate() if self.demo: - after_idle(self.top, self.demoEvent) # schedule next move + after_idle(self.top, self.demoEvent) # schedule next move # play one demo move while in the demo event def playOneDemoMove(self, demo): @@ -2582,7 +2646,7 @@ Congratulations, you did it ! return 0 def createDemoInfoText(self): - ## TODO - the text placement is not fully ok + # TODO - the text placement is not fully ok if DEBUG: self.showHelp('help', self.getDemoInfoText()) return @@ -2596,7 +2660,7 @@ Congratulations, you did it ! ] ta = self.getDemoInfoTextAttr(tinfo) if ta: - #font = self.app.getFont("canvas_large") + # font = self.app.getFont("canvas_large") font = self.app.getFont("default") self.demo.info_text = MfxCanvasText(self.canvas, ta[1], ta[2], anchor=ta[0], font=font, @@ -2647,7 +2711,6 @@ Congratulations, you did it ! return mm return -1 - def createDemoLogo(self): if not self.app.gimages.demo: return @@ -2655,7 +2718,7 @@ Congratulations, you did it ! return if self.width <= 100 or self.height <= 100: return - ##self.demo_logo = self.app.miscrandom.choice(self.app.gimages.demo) + # self.demo_logo = self.app.miscrandom.choice(self.app.gimages.demo) n = self.random.initial_seed % len(self.app.gimages.demo) self.demo_logo = self.app.gimages.demo[int(n)] self.canvas.setTopImage(self.demo_logo) @@ -2688,30 +2751,29 @@ Congratulations, you did it ! text = '' else: text = 'x' - #self.playSample("autopilotlost", priority=1000) + # self.playSample("autopilotlost", priority=1000) self.updateStatus(stuck=text) - # # Handle moves (with move history for undo/redo) # Actual move is handled in a subclass of AtomicMove. # # Note: - # All playing moves (user actions, demo games) must get routed - # to Stack.moveMove() because the stack may add important - # triggers to a move (most notably fillStack and updateModel). + # All playing moves (user actions, demo games) must get routed + # to Stack.moveMove() because the stack may add important + # triggers to a move (most notably fillStack and updateModel). # - # Only low-level game (Game.startGame, Game.dealCards, Game.fillStack) - # or stack methods (Stack.moveMove) should call the functions below - # directly. + # Only low-level game (Game.startGame, Game.dealCards, Game.fillStack) + # or stack methods (Stack.moveMove) should call the functions below + # directly. # def startMoves(self): self.moves = Struct( - state = self.S_PLAY, - history = [], # list of lists of atomic moves - index = 0, - current = [], # atomic moves for the current move + state=self.S_PLAY, + history=[], # list of lists of atomic moves + index=0, + current=[], # atomic moves for the current move ) # reset statistics self.stats.undo_moves = 0 @@ -2780,7 +2842,7 @@ Congratulations, you did it ! am = ASaveSeedMove(self) self.__storeMove(am) am.do(self) - ##self.hints.list = None + # self.hints.list = None # move type 6 def shuffleStackMove(self, stack): @@ -2796,7 +2858,7 @@ Congratulations, you did it ! am = AUpdateStackMove(stack, flags) self.__storeMove(am) am.do(self) - ##self.hints.list = None + # #self.hints.list = None # move type 8 def flipAllMove(self, stack): @@ -2811,16 +2873,16 @@ Congratulations, you did it ! am = ASaveStateMove(self, flags) self.__storeMove(am) am.do(self) - ##self.hints.list = None + # self.hints.list = None # for ArbitraryStack - def singleCardMove(self, from_stack, to_stack, position, frames=-1, shadow=-1): + def singleCardMove(self, from_stack, to_stack, position, + frames=-1, shadow=-1): am = ASingleCardMove(from_stack, to_stack, position, frames, shadow) self.__storeMove(am) am.do(self) self.hints.list = None - # Finish the current move. def finishMove(self): current, moves, stats = self.moves.current, self.moves, self.stats @@ -2847,20 +2909,21 @@ Congratulations, you did it ! for i in range(l): a1 = current[i] a2 = m[i] - if a1.__class__ is not a2.__class__ or a1.cmpForRedo(a2) != 0: + if a1.__class__ is not a2.__class__ or \ + a1.cmpForRedo(a2) != 0: break else: redo = 1 # add current move to history (which is a list of lists) if redo: - ###print "detected redo:", current + # print "detected redo:", current # overwrite existing entry because minor things like # shadow/frames may have changed moves.history[moves.index] = current moves.index += 1 else: # resize (i.e. possibly shorten list from previous undos) - moves.history[moves.index : ] = [current] + moves.history[moves.index:] = [current] moves.index += 1 assert moves.index == len(moves.history) @@ -2876,7 +2939,6 @@ Congratulations, you did it ! return 1 - # # undo/redo layer # @@ -2906,7 +2968,6 @@ Congratulations, you did it ! self.failed_snapshots = [] reset_solver_dialog() - def redo(self): assert self.canRedo() assert self.moves.state == self.S_PLAY and len(self.moves.current) == 0 @@ -2915,10 +2976,6 @@ Congratulations, you did it ! return m = self.moves.history[self.moves.index] self.moves.index += 1 - if self.moves.index == len(self.moves.history): - mm = self.moves.current - else: - mm = self.moves.history[self.moves.index] self.moves.state = self.S_REDO for atomic_move in m: atomic_move.redo(self) @@ -2933,7 +2990,6 @@ Congratulations, you did it ! self.updateStuck() reset_solver_dialog() - # # subclass hooks # @@ -2941,11 +2997,11 @@ Congratulations, you did it ! def setState(self, state): # restore saved vars (from undo/redo) pass + def getState(self): # save vars (for undo/redo) return [] - # # bookmarks # @@ -2957,8 +3013,9 @@ Congratulations, you did it ! if confirm < 0: confirm = self.app.opt.confirm if confirm and self.gsaveinfo.bookmarks.get(n): - if not self.areYouSure(_("Set bookmark"), - _("Replace existing bookmark %d ?") % (n+1)): + if not self.areYouSure( + _("Set bookmark"), + _("Replace existing bookmark %d ?") % (n+1)): return 0 file = StringIO() p = Pickler(file, 1) @@ -2997,22 +3054,22 @@ Congratulations, you did it ! self.setCursor(cursor=self.app.top_cursor) else: if update_stats: - self.stats.goto_bookmark_moves = self.stats.goto_bookmark_moves + 1 - self.gstats.goto_bookmark_moves = self.gstats.goto_bookmark_moves + 1 + self.stats.goto_bookmark_moves += 1 + self.gstats.goto_bookmark_moves += 1 self.restoreGame(game, reset=0) destruct(game) def undoGotoBookmark(self): self.gotoBookmark(-1, update_stats=0) - # # load/save # def loadGame(self, filename): if self.changed(): - if not self.areYouSure(_("Open game")): return + if not self.areYouSure(_("Open game")): + return self.finishMove() # just in case game = None self.setCursor(cursor=CURSOR_WATCH) @@ -3020,26 +3077,27 @@ Congratulations, you did it ! try: game = self._loadGame(filename, self.app) game.gstats.holded = 0 - except AssertionError, ex: + except AssertionError as ex: self.updateMenus() self.setCursor(cursor=self.app.top_cursor) - d = MfxMessageDialog(self.top, title=_("Load game error"), bitmap="error", - text=_("""\ + MfxMessageDialog( + self.top, title=_("Load game error"), bitmap="error", + text=_("""\ Error while loading game. Probably the game file is damaged, but this could also be a bug you might want to report.""")) traceback.print_exc() - except UnpicklingError, ex: + except UnpicklingError as ex: self.updateMenus() self.setCursor(cursor=self.app.top_cursor) - d = MfxExceptionDialog(self.top, ex, title=_("Load game error"), - text=_("Error while loading game")) + MfxExceptionDialog(self.top, ex, title=_("Load game error"), + text=_("Error while loading game")) except: self.updateMenus() self.setCursor(cursor=self.app.top_cursor) - d = MfxMessageDialog(self.top, title=_("Load game error"), - bitmap="error", text=_("""\ + MfxMessageDialog(self.top, title=_("Load game error"), + bitmap="error", text=_("""\ Internal error while loading game. Please report this bug.""")) @@ -3051,7 +3109,7 @@ Please report this bug.""")) self.filename = filename game.filename = filename # now start the new game - ##print game.__dict__ + # print game.__dict__ if self.nextGameFlags(game.id) == 0: self.endGame() self.restoreGame(game) @@ -3060,21 +3118,19 @@ Please report this bug.""")) self.endGame() self.quitGame(game.id, loadedgame=game) - def saveGame(self, filename, protocol=-1): self.finishMove() # just in case self.setCursor(cursor=CURSOR_WATCH) try: self._saveGame(filename, protocol) - except Exception, ex: + except Exception as ex: self.setCursor(cursor=self.app.top_cursor) - d = MfxExceptionDialog(self.top, ex, title=_("Save game error"), - text=_("Error while saving game")) + MfxExceptionDialog(self.top, ex, title=_("Save game error"), + text=_("Error while saving game")) else: self.filename = filename self.setCursor(cursor=self.app.top_cursor) - # # low level load/save # @@ -3088,7 +3144,8 @@ Please report this bug.""")) game = self._undumpGame(p, app) game.gstats.loaded = game.gstats.loaded + 1 finally: - if f: f.close() + if f: + f.close() return game def _undumpGame(self, p, app): @@ -3096,11 +3153,13 @@ Please report this bug.""")) # err_txt = _("Invalid or damaged %s save file") % PACKAGE # + def pload(t=None, p=p): obj = p.load() if isinstance(t, type): assert isinstance(obj, t), err_txt return obj + def validate(v, txt): if not v: raise UnpicklingError(txt) @@ -3108,9 +3167,9 @@ Please report this bug.""")) package = pload(str) validate(package == PACKAGE, err_txt) version = pload(str) - #validate(isinstance(version, str) and len(version) <= 20, err_txt) + # validate(isinstance(version, str) and len(version) <= 20, err_txt) version_tuple = pload(tuple) - validate(version_tuple >= (1,0), _('''\ + validate(version_tuple >= (1, 0), _('''\ Cannot load games saved with %s version %s''') % (PACKAGE, version)) game_version = 1 @@ -3138,8 +3197,8 @@ in the current implementation.''') % version) game.random = constructRandom(initial_seed) state = pload() game.random.setstate(state) - #if not hasattr(game.random, "origin"): - # game.random.origin = game.random.ORIGIN_UNKNOWN + # if not hasattr(game.random, "origin"): + # game.random.origin = game.random.ORIGIN_UNKNOWN game.loadinfo.stacks = [] game.loadinfo.ncards = 0 nstacks = pload(int) @@ -3191,7 +3250,8 @@ in the current implementation.''') % version) p = Pickler(f, protocol) self._dumpGame(p) finally: - if f: f.close() + if f: + f.close() def _dumpGame(self, p, bookmark=0): self.updateTime() @@ -3234,7 +3294,8 @@ in the current implementation.''') % version) def startPlayTimer(self): self.updateStatus(time=None) self.stopPlayTimer() - self.play_timer = after(self.top, PLAY_TIME_TIMEOUT, self.updatePlayTime) + self.play_timer = after( + self.top, PLAY_TIME_TIMEOUT, self.updatePlayTime) def stopPlayTimer(self): if hasattr(self, 'play_timer') and self.play_timer: @@ -3243,14 +3304,16 @@ in the current implementation.''') % version) self.updatePlayTime(do_after=0) def updatePlayTime(self, do_after=1): - if not self.top: return - if self.pause or self.finished: return + if not self.top: + return + if self.pause or self.finished: + return if do_after: - self.play_timer = after(self.top, PLAY_TIME_TIMEOUT, self.updatePlayTime) + self.play_timer = after( + self.top, PLAY_TIME_TIMEOUT, self.updatePlayTime) d = time.time() - self.stats.update_time + self.stats.elapsed_time self.updateStatus(time=format_time(d)) - # # Pause # @@ -3264,7 +3327,7 @@ in the current implementation.''') % version) self.updateTime() self.pause = not self.pause if self.pause: - ##self.updateTime() + # self.updateTime() self.canvas.hideAllItems() n = self.random.initial_seed % len(self.app.gimages.pause) self.pause_logo = self.app.gimages.pause[int(n)] @@ -3317,7 +3380,7 @@ in the current implementation.''') % version) return True return False - ## for find_card_dialog + # for find_card_dialog def canFindCard(self): return self.gameinfo.category == GI.GC_FRENCH @@ -3333,4 +3396,3 @@ in the current implementation.''') % version) def _saveGameHook(self, p): pass - diff --git a/pysollib/gamedb.py b/pysollib/gamedb.py index f2f6c1e3..4d110d3f 100644 --- a/pysollib/gamedb.py +++ b/pysollib/gamedb.py @@ -1,28 +1,29 @@ #!/usr/bin/env python # -*- mode: python; coding: utf-8; -*- -##---------------------------------------------------------------------------## -## -## Copyright (C) 1998-2003 Markus Franz Xaver Johannes Oberhumer -## Copyright (C) 2003 Mt. Hood Playing Card Co. -## Copyright (C) 2005-2009 Skomoroh -## -## 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 . -## -##---------------------------------------------------------------------------## +# ---------------------------------------------------------------------------## +# +# Copyright (C) 1998-2003 Markus Franz Xaver Johannes Oberhumer +# Copyright (C) 2003 Mt. Hood Playing Card Co. +# Copyright (C) 2005-2009 Skomoroh +# +# 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 . +# +# ---------------------------------------------------------------------------## # imports +import sys import imp # PySol imports @@ -32,78 +33,83 @@ import pysollib.settings from pysollib.mygettext import _, n_ +if sys.version_info > (3,): + basestring = str + unicode = str + # ************************************************************************ # * constants # ************************************************************************ + # GameInfo constants class GI: # game category - these *must* match the cardset CSI.TYPE_xxx - GC_FRENCH = CSI.TYPE_FRENCH - GC_HANAFUDA = CSI.TYPE_HANAFUDA - GC_TAROCK = CSI.TYPE_TAROCK - GC_MAHJONGG = CSI.TYPE_MAHJONGG - GC_HEXADECK = CSI.TYPE_HEXADECK + GC_FRENCH = CSI.TYPE_FRENCH + GC_HANAFUDA = CSI.TYPE_HANAFUDA + GC_TAROCK = CSI.TYPE_TAROCK + GC_MAHJONGG = CSI.TYPE_MAHJONGG + GC_HEXADECK = CSI.TYPE_HEXADECK GC_MUGHAL_GANJIFA = CSI.TYPE_MUGHAL_GANJIFA GC_NAVAGRAHA_GANJIFA = CSI.TYPE_NAVAGRAHA_GANJIFA GC_DASHAVATARA_GANJIFA = CSI.TYPE_DASHAVATARA_GANJIFA - GC_TRUMP_ONLY = CSI.TYPE_TRUMP_ONLY + GC_TRUMP_ONLY = CSI.TYPE_TRUMP_ONLY # game type - GT_1DECK_TYPE = 0 - GT_2DECK_TYPE = 1 - GT_3DECK_TYPE = 2 - GT_4DECK_TYPE = 3 + GT_1DECK_TYPE = 0 + GT_2DECK_TYPE = 1 + GT_3DECK_TYPE = 2 + GT_4DECK_TYPE = 3 GT_BAKERS_DOZEN = 4 GT_BELEAGUERED_CASTLE = 5 - GT_CANFIELD = 6 + GT_CANFIELD = 6 GT_DASHAVATARA_GANJIFA = 7 - GT_FAN_TYPE = 8 + GT_FAN_TYPE = 8 GT_FORTY_THIEVES = 9 - GT_FREECELL = 10 - GT_GOLF = 11 - GT_GYPSY = 12 - GT_HANAFUDA = 13 - GT_HEXADECK = 14 - GT_KLONDIKE = 15 - GT_MAHJONGG = 16 - GT_MATRIX = 17 - GT_MEMORY = 18 - GT_MONTANA = 19 + GT_FREECELL = 10 + GT_GOLF = 11 + GT_GYPSY = 12 + GT_HANAFUDA = 13 + GT_HEXADECK = 14 + GT_KLONDIKE = 15 + GT_MAHJONGG = 16 + GT_MATRIX = 17 + GT_MEMORY = 18 + GT_MONTANA = 19 GT_MUGHAL_GANJIFA = 20 - GT_NAPOLEON = 21 + GT_NAPOLEON = 21 GT_NAVAGRAHA_GANJIFA = 22 - GT_NUMERICA = 23 + GT_NUMERICA = 23 GT_PAIRING_TYPE = 24 - GT_POKER_TYPE = 25 - GT_PUZZLE_TYPE = 26 - GT_RAGLAN = 27 - GT_ROW_TYPE = 28 - GT_SIMPLE_TYPE = 29 - GT_SPIDER = 30 - GT_TAROCK = 31 - GT_TERRACE = 32 - GT_YUKON = 33 - GT_SHISEN_SHO = 34 - GT_CUSTOM = 40 + GT_POKER_TYPE = 25 + GT_PUZZLE_TYPE = 26 + GT_RAGLAN = 27 + GT_ROW_TYPE = 28 + GT_SIMPLE_TYPE = 29 + GT_SPIDER = 30 + GT_TAROCK = 31 + GT_TERRACE = 32 + GT_YUKON = 33 + GT_SHISEN_SHO = 34 + GT_CUSTOM = 40 # extra flags - GT_BETA = 1 << 12 # beta version of game driver - GT_CHILDREN = 1 << 13 # *not used* - GT_CONTRIB = 1 << 14 # contributed games under the GNU GPL - GT_HIDDEN = 1 << 15 # not visible in menus, but games can be loaded - GT_OPEN = 1 << 16 - GT_ORIGINAL = 1 << 17 - GT_POPULAR = 1 << 18 # *not used* - GT_RELAXED = 1 << 19 - GT_SCORE = 1 << 20 # game has some type of scoring + GT_BETA = 1 << 12 # beta version of game driver + GT_CHILDREN = 1 << 13 # *not used* + GT_CONTRIB = 1 << 14 # contributed games under the GNU GPL + GT_HIDDEN = 1 << 15 # not visible in menus, but games can be loaded + GT_OPEN = 1 << 16 + GT_ORIGINAL = 1 << 17 + GT_POPULAR = 1 << 18 # *not used* + GT_RELAXED = 1 << 19 + GT_SCORE = 1 << 20 # game has some type of scoring GT_SEPARATE_DECKS = 1 << 21 - GT_XORIGINAL = 1 << 22 # original games by other people, not playable + GT_XORIGINAL = 1 << 22 # original games by other people, not playable # skill level - SL_LUCK = 1 - SL_MOSTLY_LUCK = 2 - SL_BALANCED = 3 + SL_LUCK = 1 + SL_MOSTLY_LUCK = 2 + SL_BALANCED = 3 SL_MOSTLY_SKILL = 4 - SL_SKILL = 5 + SL_SKILL = 5 # TYPE_NAMES = { GT_BAKERS_DOZEN: n_("Baker's Dozen"), @@ -130,75 +136,115 @@ class GI: GT_4DECK_TYPE: n_("Four-Deck games"), } -## SELECT_GAME_BY_TYPE = [] -## for gt, name in TYPE_NAMES.items(): -## if not name.endswith('games'): -## name = name+n_(' type') -## SELECT_GAME_BY_TYPE.append( -## (name, lambda gi, gt=gt: gi.si.game_type == gt)) -## SELECT_GAME_BY_TYPE = tuple(SELECT_GAME_BY_TYPE) + # SELECT_GAME_BY_TYPE = [] + # for gt, name in TYPE_NAMES.items(): + # if not name.endswith('games'): + # name = name+n_(' type') + # SELECT_GAME_BY_TYPE.append( + # (name, lambda gi, gt=gt: gi.si.game_type == gt)) + # SELECT_GAME_BY_TYPE = tuple(SELECT_GAME_BY_TYPE) SELECT_GAME_BY_TYPE = ( - (n_("Baker's Dozen type"),lambda gi, gt=GT_BAKERS_DOZEN: gi.si.game_type == gt), - (n_("Beleaguered Castle type"),lambda gi, gt=GT_BELEAGUERED_CASTLE: gi.si.game_type == gt), - (n_("Canfield type"), lambda gi, gt=GT_CANFIELD: gi.si.game_type == gt), - (n_("Fan type"), lambda gi, gt=GT_FAN_TYPE: gi.si.game_type == gt), - (n_("Forty Thieves type"),lambda gi, gt=GT_FORTY_THIEVES: gi.si.game_type == gt), - (n_("FreeCell type"), lambda gi, gt=GT_FREECELL: gi.si.game_type == gt), - (n_("Golf type"), lambda gi, gt=GT_GOLF: gi.si.game_type == gt), - (n_("Gypsy type"), lambda gi, gt=GT_GYPSY: gi.si.game_type == gt), - (n_("Klondike type"), lambda gi, gt=GT_KLONDIKE: gi.si.game_type == gt), - (n_("Montana type"), lambda gi, gt=GT_MONTANA: gi.si.game_type == gt), - (n_("Napoleon type"), lambda gi, gt=GT_NAPOLEON: gi.si.game_type == gt), - (n_("Numerica type"), lambda gi, gt=GT_NUMERICA: gi.si.game_type == gt), - (n_("Pairing type"), lambda gi, gt=GT_PAIRING_TYPE: gi.si.game_type == gt), - (n_("Raglan type"), lambda gi, gt=GT_RAGLAN: gi.si.game_type == gt), - (n_("Simple games"), lambda gi, gt=GT_SIMPLE_TYPE: gi.si.game_type == gt), - (n_("Spider type"), lambda gi, gt=GT_SPIDER: gi.si.game_type == gt), - (n_("Terrace type"), lambda gi, gt=GT_TERRACE: gi.si.game_type == gt), - (n_("Yukon type"), lambda gi, gt=GT_YUKON: gi.si.game_type == gt), - (n_("One-Deck games"),lambda gi, gt=GT_1DECK_TYPE: gi.si.game_type == gt), - (n_("Two-Deck games"),lambda gi, gt=GT_2DECK_TYPE: gi.si.game_type == gt), - (n_("Three-Deck games"),lambda gi, gt=GT_3DECK_TYPE: gi.si.game_type == gt), - (n_("Four-Deck games"),lambda gi, gt=GT_4DECK_TYPE: gi.si.game_type == gt), + (n_("Baker's Dozen type"), lambda gi, + gt=GT_BAKERS_DOZEN: gi.si.game_type == gt), + (n_("Beleaguered Castle type"), + lambda gi, gt=GT_BELEAGUERED_CASTLE: gi.si.game_type == gt), + (n_("Canfield type"), + lambda gi, gt=GT_CANFIELD: gi.si.game_type == gt), + (n_("Fan type"), lambda gi, gt=GT_FAN_TYPE: gi.si.game_type == gt), + (n_("Forty Thieves type"), + lambda gi, gt=GT_FORTY_THIEVES: gi.si.game_type == gt), + (n_("FreeCell type"), + lambda gi, gt=GT_FREECELL: gi.si.game_type == gt), + (n_("Golf type"), lambda gi, gt=GT_GOLF: gi.si.game_type == gt), + (n_("Gypsy type"), lambda gi, gt=GT_GYPSY: gi.si.game_type == gt), + (n_("Klondike type"), + lambda gi, gt=GT_KLONDIKE: gi.si.game_type == gt), + (n_("Montana type"), lambda gi, gt=GT_MONTANA: gi.si.game_type == gt), + (n_("Napoleon type"), + lambda gi, gt=GT_NAPOLEON: gi.si.game_type == gt), + (n_("Numerica type"), + lambda gi, gt=GT_NUMERICA: gi.si.game_type == gt), + (n_("Pairing type"), + lambda gi, gt=GT_PAIRING_TYPE: gi.si.game_type == gt), + (n_("Raglan type"), lambda gi, gt=GT_RAGLAN: gi.si.game_type == gt), + (n_("Simple games"), + lambda gi, gt=GT_SIMPLE_TYPE: gi.si.game_type == gt), + (n_("Spider type"), lambda gi, gt=GT_SPIDER: gi.si.game_type == gt), + (n_("Terrace type"), lambda gi, gt=GT_TERRACE: gi.si.game_type == gt), + (n_("Yukon type"), lambda gi, gt=GT_YUKON: gi.si.game_type == gt), + (n_("One-Deck games"), + lambda gi, gt=GT_1DECK_TYPE: gi.si.game_type == gt), + (n_("Two-Deck games"), + lambda gi, gt=GT_2DECK_TYPE: gi.si.game_type == gt), + (n_("Three-Deck games"), + lambda gi, gt=GT_3DECK_TYPE: gi.si.game_type == gt), + (n_("Four-Deck games"), + lambda gi, gt=GT_4DECK_TYPE: gi.si.game_type == gt), ) SELECT_ORIGINAL_GAME_BY_TYPE = ( - (n_("French type"), lambda gi, gf=GT_ORIGINAL, gt=(GT_HANAFUDA, GT_HEXADECK, GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, GT_DASHAVATARA_GANJIFA, GT_TAROCK,): gi.si.game_flags & gf and gi.si.game_type not in gt), - (n_("Ganjifa type"), lambda gi, gf=GT_ORIGINAL, gt=(GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, GT_DASHAVATARA_GANJIFA,): gi.si.game_flags & gf and gi.si.game_type in gt), - (n_("Hanafuda type"), lambda gi, gf=GT_ORIGINAL, gt=GT_HANAFUDA: gi.si.game_flags & gf and gi.si.game_type == gt), - (n_("Hex A Deck type"), lambda gi, gf=GT_ORIGINAL, gt=GT_HEXADECK: gi.si.game_flags & gf and gi.si.game_type == gt), - (n_("Tarock type"), lambda gi, gf=GT_ORIGINAL, gt=GT_TAROCK: gi.si.game_flags & gf and gi.si.game_type == gt), + (n_("French type"), lambda gi, gf=GT_ORIGINAL, + gt=( + GT_HANAFUDA, + GT_HEXADECK, GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, + GT_DASHAVATARA_GANJIFA, GT_TAROCK,): gi.si.game_flags & gf and + gi.si.game_type not in gt), + (n_("Ganjifa type"), lambda gi, gf=GT_ORIGINAL, + gt=(GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, + GT_DASHAVATARA_GANJIFA,): gi.si.game_flags & gf and + gi.si.game_type in gt), + (n_("Hanafuda type"), lambda gi, gf=GT_ORIGINAL, gt=GT_HANAFUDA: + gi.si.game_flags & gf and gi.si.game_type == gt), + (n_("Hex A Deck type"), lambda gi, gf=GT_ORIGINAL, gt=GT_HEXADECK: + gi.si.game_flags & gf and gi.si.game_type == gt), + (n_("Tarock type"), lambda gi, gf=GT_ORIGINAL, gt=GT_TAROCK: + gi.si.game_flags & gf and gi.si.game_type == gt), ) SELECT_CONTRIB_GAME_BY_TYPE = ( - (n_("French type"), lambda gi, gf=GT_CONTRIB, gt=(GT_HANAFUDA, GT_HEXADECK, GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, GT_DASHAVATARA_GANJIFA, GT_TAROCK,): gi.si.game_flags & gf and gi.si.game_type not in gt), - (n_("Ganjifa type"), lambda gi, gf=GT_CONTRIB, gt=(GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, GT_DASHAVATARA_GANJIFA,): gi.si.game_flags & gf and gi.si.game_type in gt), - (n_("Hanafuda type"), lambda gi, gf=GT_CONTRIB, gt=GT_HANAFUDA: gi.si.game_flags & gf and gi.si.game_type == gt), - (n_("Hex A Deck type"), lambda gi, gf=GT_CONTRIB, gt=GT_HEXADECK: gi.si.game_flags & gf and gi.si.game_type == gt), - (n_("Tarock type"), lambda gi, gf=GT_CONTRIB, gt=GT_TAROCK: gi.si.game_flags & gf and gi.si.game_type == gt), + (n_("French type"), lambda gi, gf=GT_CONTRIB, + gt=(GT_HANAFUDA, GT_HEXADECK, GT_MUGHAL_GANJIFA, + GT_NAVAGRAHA_GANJIFA, GT_DASHAVATARA_GANJIFA, GT_TAROCK,): + gi.si.game_flags & gf and gi.si.game_type not in gt), + (n_("Ganjifa type"), lambda gi, gf=GT_CONTRIB, + gt=(GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, + GT_DASHAVATARA_GANJIFA,): + gi.si.game_flags & gf and gi.si.game_type in gt), + (n_("Hanafuda type"), lambda gi, gf=GT_CONTRIB, gt=GT_HANAFUDA: + gi.si.game_flags & gf and gi.si.game_type == gt), + (n_("Hex A Deck type"), lambda gi, gf=GT_CONTRIB, gt=GT_HEXADECK: + gi.si.game_flags & gf and gi.si.game_type == gt), + (n_("Tarock type"), lambda gi, gf=GT_CONTRIB, gt=GT_TAROCK: + gi.si.game_flags & gf and gi.si.game_type == gt), ) SELECT_ORIENTAL_GAME_BY_TYPE = ( - (n_("Dashavatara Ganjifa type"), lambda gi, gt=GT_DASHAVATARA_GANJIFA: gi.si.game_type == gt), - (n_("Ganjifa type"), lambda gi, gt=(GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, GT_DASHAVATARA_GANJIFA,): gi.si.game_type in gt), - (n_("Hanafuda type"), lambda gi, gt=GT_HANAFUDA: gi.si.game_type == gt), - (n_("Mughal Ganjifa type"), lambda gi, gt=GT_MUGHAL_GANJIFA: gi.si.game_type == gt), - (n_("Navagraha Ganjifa type"), lambda gi, gt=GT_NAVAGRAHA_GANJIFA: gi.si.game_type == gt), + (n_("Dashavatara Ganjifa type"), lambda gi, gt=GT_DASHAVATARA_GANJIFA: + gi.si.game_type == gt), + (n_("Ganjifa type"), lambda gi, + gt=(GT_MUGHAL_GANJIFA, GT_NAVAGRAHA_GANJIFA, + GT_DASHAVATARA_GANJIFA,): gi.si.game_type in gt), + (n_("Hanafuda type"), + lambda gi, gt=GT_HANAFUDA: gi.si.game_type == gt), + (n_("Mughal Ganjifa type"), + lambda gi, gt=GT_MUGHAL_GANJIFA: gi.si.game_type == gt), + (n_("Navagraha Ganjifa type"), + lambda gi, gt=GT_NAVAGRAHA_GANJIFA: gi.si.game_type == gt), ) SELECT_SPECIAL_GAME_BY_TYPE = ( - (n_("Shisen-Sho"), lambda gi, gt=GT_SHISEN_SHO: gi.si.game_type == gt), - (n_("Hex A Deck type"), lambda gi, gt=GT_HEXADECK: gi.si.game_type == gt), - (n_("Matrix type"), lambda gi, gt=GT_MATRIX: gi.si.game_type == gt), - (n_("Memory type"), lambda gi, gt=GT_MEMORY: gi.si.game_type == gt), - (n_("Poker type"), lambda gi, gt=GT_POKER_TYPE: gi.si.game_type == gt), - (n_("Puzzle type"), lambda gi, gt=GT_PUZZLE_TYPE: gi.si.game_type == gt), - (n_("Tarock type"), lambda gi, gt=GT_TAROCK: gi.si.game_type == gt), + (n_("Shisen-Sho"), lambda gi, gt=GT_SHISEN_SHO: gi.si.game_type == gt), + (n_("Hex A Deck type"), + lambda gi, gt=GT_HEXADECK: gi.si.game_type == gt), + (n_("Matrix type"), lambda gi, gt=GT_MATRIX: gi.si.game_type == gt), + (n_("Memory type"), lambda gi, gt=GT_MEMORY: gi.si.game_type == gt), + (n_("Poker type"), lambda gi, gt=GT_POKER_TYPE: gi.si.game_type == gt), + (n_("Puzzle type"), + lambda gi, gt=GT_PUZZLE_TYPE: gi.si.game_type == gt), + (n_("Tarock type"), lambda gi, gt=GT_TAROCK: gi.si.game_type == gt), ) - - # These obsolete gameids have been used in previous versions of # PySol and are no longer supported because of internal changes # (mainly rule changes). The game has been assigned a new id. @@ -209,31 +255,31 @@ class GI: 72: 115, # Little Forty 75: 126, # Red and Black 82: 901, # La Belle Lucie (Midnight Oil) -## 155: 5034, # Mahjongg - Flying Dragon -## 156: 5035, # Mahjongg - Fortress Towers - 262: 105, # Canfield - 902: 88, # Trefoil - 904: 68, # Lexington Harp - 297: 631, # Alternation/Alternations + # 155: 5034, # Mahjongg - Flying Dragon + # 156: 5035, # Mahjongg - Fortress Towers + 262: 105, # Canfield + 902: 88, # Trefoil + 904: 68, # Lexington Harp + 297: 631, # Alternation/Alternations } GAMES_BY_COMPATIBILITY = ( # Atari ST Patience game v2.13 (we have 10 out of 10 games) ("Atari ST Patience", (1, 3, 4, 7, 12, 14, 15, 16, 17, 39,)), - ## Gnome AisleRiot 1.0.51 (we have 28 out of 32 games) - ## still missing: Camelot, Clock, Thieves, Thirteen - ##("Gnome AisleRiot 1.0.51", ( - ## 2, 8, 11, 19, 27, 29, 33, 34, 35, 40, - ## 41, 42, 43, 58, 59, 92, 93, 94, 95, 96, - ## 100, 105, 111, 112, 113, 130, 200, 201, - ##)), - ## Gnome AisleRiot 1.4.0.1 (we have XX out of XX games) - ##("Gnome AisleRiot", ( - ## 1, 2, 8, 11, 19, 27, 29, 33, 34, 35, 40, - ## 41, 42, 43, 58, 59, 92, 93, 94, 95, 96, - ## 100, 105, 111, 112, 113, 130, 200, 201, - ##)), + # Gnome AisleRiot 1.0.51 (we have 28 out of 32 games) + # still missing: Camelot, Clock, Thieves, Thirteen + # ("Gnome AisleRiot 1.0.51", ( + # 2, 8, 11, 19, 27, 29, 33, 34, 35, 40, + # 41, 42, 43, 58, 59, 92, 93, 94, 95, 96, + # 100, 105, 111, 112, 113, 130, 200, 201, + # )), + # Gnome AisleRiot 1.4.0.1 (we have XX out of XX games) + # ("Gnome AisleRiot", ( + # 1, 2, 8, 11, 19, 27, 29, 33, 34, 35, 40, + # 41, 42, 43, 58, 59, 92, 93, 94, 95, 96, + # 100, 105, 111, 112, 113, 130, 200, 201, + # )), # Gnome AisleRiot 2.2.0 (we have 61 out of 70 games) # still missing: # Gay gordons, Helsinki, @@ -247,12 +293,12 @@ class GI: 283, 284, 551, 552, 553, 737, )), - ## KDE Patience 0.7.3 from KDE 1.1.2 (we have 6 out of 9 games) - ##("KDE Patience 0.7.3", (2, 7, 8, 18, 256, 903,)), - ## KDE Patience 2.0 from KDE 2.1.2 (we have 11 out of 13 games) - ##("KDE Patience", (1, 2, 7, 8, 18, 19, 23, 50, 256, 261, 903,)), - ## KDE Patience 2.0 from KDE 2.2beta1 (we have 12 out of 14 games) - ##("KDE Patience", (1, 2, 7, 8, 18, 19, 23, 36, 50, 256, 261, 903,)), + # KDE Patience 0.7.3 from KDE 1.1.2 (we have 6 out of 9 games) + # ("KDE Patience 0.7.3", (2, 7, 8, 18, 256, 903,)), + # KDE Patience 2.0 from KDE 2.1.2 (we have 11 out of 13 games) + # ("KDE Patience", (1, 2, 7, 8, 18, 19, 23, 50, 256, 261, 903,)), + # KDE Patience 2.0 from KDE 2.2beta1 (we have 12 out of 14 games) + # ("KDE Patience", (1, 2, 7, 8, 18, 19, 23, 36, 50, 256, 261, 903,)), # KDE Patience 2.0 from KDE 3.1.1 (we have 15 out of 15 games) ("KDE Patience", (1, 2, 7, 8, 18, 19, 23, 36, 50, 256, 261, 277, 278, 279, 903,)), @@ -303,9 +349,9 @@ class GI: ("2.99", (37,)), ("3.00", (38, 39, 40, 41, 42, 43, 45, 46, 47, 48, 49, - 50, 51,903, 53, 54, 55, 56, 57, 58, 59, + 50, 51, 903, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, - 70, 71,115, 73, 74,126, 76, 77, 78, 79, + 70, 71, 115, 73, 74, 126, 76, 77, 78, 79, 80, 81, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 107, 108,)), @@ -317,7 +363,7 @@ class GI: ("3.21", (143, 144)), ("3.30", (145, 146, 147, 148, 149, 150, 151)), ("3.40", (152, 153, 154)), - ("4.00", ( 157, 158, 159, 160, 161, 162, 163, 164)), + ("4.00", (157, 158, 159, 160, 161, 162, 163, 164)), ("4.20", (165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, 178)), ("4.30", (179, 180, 181, 182, 183, 184)), @@ -329,8 +375,8 @@ class GI: 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236)), ("4.70", (237,)), - ('fc-0.5.0', ( # moved from Ultrasol - #121, 122, 187, 188, 189, 190, 191, 192, 194, 197, 198, + ('fc-0.5.0', ( # moved from Ultrasol + # 121, 122, 187, 188, 189, 190, 191, 192, 194, 197, 198, 5301, 5302, 9011, 11001, 11002, 11003, 11004, 11005, 11006, 12353, 12354, 12355, 12356, 12357, 12358, 12359, 12360, 12361, 12362, 12363, 12364, 12365, 12366, 12367, @@ -347,7 +393,7 @@ class GI: 16674, 16675, 16676, 16677, 16678, 16679, 16680, 22216, 22223, 22224, 22225, 22226, 22227, 22228, 22229, 22230, 22231, 22232,)), - ('fc-0.8.0', tuple(range(263, 323))), # exclude 297 + ('fc-0.8.0', tuple(range(263, 323))), # exclude 297 ('fc-0.9.0', tuple(range(323, 421))), ('fc-0.9.1', tuple(range(421, 441))), ('fc-0.9.2', tuple(range(441, 466))), @@ -355,12 +401,12 @@ class GI: ('fc-0.9.4', tuple(range(661, 671))), ('fc-1.0', tuple(range(671, 711))), ('fc-1.1', tuple(range(711, 759))), - ('fc-2.0', tuple(range(11011, 11014)) + tuple(range(759, 767)) ), + ('fc-2.0', tuple(range(11011, 11014)) + tuple(range(759, 767))), ) # deprecated - the correct way is to or a GI.GT_XXX flag # in the registerGame() call - _CHILDREN_GAMES = [16, 33, 55, 90, 91, 96, 97, 176, 903,] + _CHILDREN_GAMES = [16, 33, 55, 90, 91, 96, 97, 176, 903, ] _OPEN_GAMES = [] @@ -384,7 +430,7 @@ class GI: 903, # Ace Up 5034, # Mahjongg Flying Dragon 5401, # Mahjongg Taipei - 12345, # Oonsoo + 12345, # Oonsoo ] @@ -412,7 +458,7 @@ class GameInfo(Struct): return s try: s = unicode(s, 'utf-8') - except UnicodeDecodeError, err: + except UnicodeDecodeError as err: print_err(err) s = unicode(s, 'utf-8', 'ignore') return s @@ -456,11 +502,13 @@ class GameInfo(Struct): if not (1 <= id <= 999999): raise GameInfoException(name+": invalid game ID "+str(id)) if category == GI.GC_MAHJONGG: - if decks%4: - raise GameInfoException(name+": invalid number of decks "+str(id)) + if decks % 4: + raise GameInfoException(name+": invalid number of decks " + + str(id)) else: if not (1 <= decks <= 4): - raise GameInfoException(name+": invalid number of decks "+str(id)) + raise GameInfoException( + name+": invalid number of decks "+str(id)) if not name: raise GameInfoException(name+": invalid game name") if GI.PROTECTED_GAMES.get(id): @@ -521,7 +569,7 @@ class GameManager: return self.__all_games.get(key) def _check_game(self, gi): - ##print 'check game:', gi.id, gi.short_name.encode('utf-8') + # print 'check game:', gi.id, gi.short_name.encode('utf-8') if gi.id in self.__all_games: raise GameInfoException("duplicate game ID %s: %s and %s" % (gi.id, str(gi.gameclass), @@ -543,14 +591,14 @@ class GameManager: (gi.id, n)) def register(self, gi): - ##print gi.id, gi.short_name.encode('utf-8') + # print gi.id, gi.short_name.encode('utf-8') if not isinstance(gi, GameInfo): raise GameInfoException("wrong GameInfo class") if self.check_game and pysollib.settings.CHECK_GAMES: self._check_game(gi) - ##if 0 and gi.si.game_flags & GI.GT_XORIGINAL: - ## return - ##print gi.id, gi.name + # if 0 and gi.si.game_flags & GI.GT_XORIGINAL: + # return + # print gi.id, gi.name self.__all_games[gi.id] = gi self.__all_gamenames[gi.name] = gi for n in gi.altnames: @@ -565,12 +613,13 @@ class GameManager: self.__games_by_name = None # update registry k = gi.si.game_type - self.registered_game_types[k] = self.registered_game_types.get(k, 0) + 1 -## if not gi.si.game_type == GI.GT_MAHJONGG: -## for v, k in GI.GAMES_BY_PYSOL_VERSION: -## if gi.id in k: break -## else: -## print gi.id + self.registered_game_types[k] = \ + self.registered_game_types.get(k, 0) + 1 +# if not gi.si.game_type == GI.GT_MAHJONGG: +# for v, k in GI.GAMES_BY_PYSOL_VERSION: +# if gi.id in k: break +# else: +# print gi.id if hasattr(gi.gameclass, 'Solver_Class') and \ gi.gameclass.Solver_Class is not None: self.__games_for_solver.append(gi.id) @@ -586,7 +635,7 @@ class GameManager: # def getAllGames(self): - ##return self.__all_games + # return self.__all_games return self.__games.values() def getGamesIdSortedById(self): @@ -598,15 +647,15 @@ class GameManager: def getGamesIdSortedByName(self): if self.__games_by_name is None: - l1, l2, l3 = [], [], [] + l1, l2, l3 = [], [], [] for id, gi in self.__games.items(): - name = gi.name #.lower() + name = gi.name # .lower() l1.append((name, id)) if gi.name != gi.short_name: - name = gi.short_name #.lower() + name = gi.short_name # .lower() l2.append((name, id)) for n in gi.altnames: - name = n #.lower() + name = n # .lower() l3.append((name, id, n)) l1.sort() l2.sort() @@ -652,10 +701,9 @@ def registerGame(gameinfo): def loadGame(modname, filename, check_game=False): - ##print "load game", modname, filename + # print "load game", modname, filename GAME_DB.check_game = check_game GAME_DB.current_filename = filename - module = imp.load_source(modname, filename) - ##execfile(filename, globals(), globals()) + imp.load_source(modname, filename) + # execfile(filename, globals(), globals()) GAME_DB.current_filename = None - diff --git a/tests/style/py-flake8.t b/tests/style/py-flake8.t index cdf85ef7..16ce3152 100644 --- a/tests/style/py-flake8.t +++ b/tests/style/py-flake8.t @@ -9,7 +9,7 @@ use Test::Differences qw( eq_or_diff ); use String::ShellQuote qw/ shell_quote /; # my $cmd = shell_quote( 'flake8', '.' ); -my $cmd = shell_quote( 'flake8', glob('./pysollib/[a-c]*.py') ); +my $cmd = shell_quote( 'flake8', glob('./pysollib/[a-g]*.py') ); # TEST eq_or_diff( scalar(`$cmd`), '', "flake8 is happy with the code." );