[prev in list] [next in list] [prev in thread] [next in thread]
List: kde-commits
Subject: playground/games/kmj
From: Wolfgang Rohdewald <wolfgang () rohdewald ! de>
Date: 2009-02-26 13:46:38
Message-ID: 1235655998.960640.6333.nullmailer () svn ! kde ! org
[Download RAW message or body]
SVN commit 932374 by wrohdewald:
introducing Walls.divide()
M +90 -28 board.py
M +6 -7 kmj.py
--- trunk/playground/games/kmj/board.py #932373:932374
@@ -35,20 +35,30 @@
the unit of xoffset is the width of the tile,
the unit of yoffset is the height of the tile.
"""
- def __init__(self, element, xoffset = 0, yoffset = 0, level=0):
+ def __init__(self, element, xoffset = 0, yoffset = 0, level=0, faceDown=False):
QGraphicsSvgItem.__init__(self)
self.__board = None
self.element = element
self.selected = False
+ self.__faceDown = faceDown
self.level = level
self.xoffset = xoffset
self.yoffset = yoffset
self.face = None
- def xmousePressEvent(self, event):
+ def mousePressEvent(self, event):
"""selects the tile. While moving, it should be above all other tiles"""
+ # TODO: find out which tile is clicked on. Do not react when clicking on shadow...
+ for tile in self.collidingItems():
+ if isinstance(tile, Tile) and tile.zValue() > self.zValue():
+ print 'other tile %s has z=%d, we(%s) have z=%d' \
+ % (tile.element, tile.zValue(), self.element, self.zValue())
+ QGraphicsSvgItem.mousePressEvent(self, event)
+ return
# self.setZValue(1000000000)
+# self.select()
print 'mousepos:', self.mapToScene(event.pos())
+ print 'tile:', self.element
print 'tilerect:', self.mapToScene(self.boundingRect()).boundingRect()
print 'tileset.tilesize:', self.tileset.tileSize
if self.face:
@@ -75,11 +85,15 @@
def setBoard(self, board):
"""assign the tile to a board and define it according to the board parameters"""
- if self.__board and board != self.__board:
- logException(TileException('Tile can only belong to one board'))
+# if self.__board and board != self.__board:
+ # logException(TileException('Tile can only belong to one board'))
+ self.__board = board
+ self.recompute()
+
+ def recompute(self):
+ """recomputes position and visuals of the tile"""
self.prepareGeometryChange()
- self.__board = board
- self.setParentItem(board)
+ self.setParentItem(self.__board)
self.placeInScene()
self.setSharedRenderer(self.tileset.renderer())
lightSource = self.board.lightSource
@@ -93,7 +107,7 @@
xoffset = shadowWidth-1
if 'S' in lightSource:
yoffset = shadowHeight-1
- if self.element:
+ if self.element and not self.faceDown:
if not self.face:
self.face = QGraphicsSvgItem()
self.face.setParentItem(self)
@@ -102,12 +116,31 @@
# by shadow width
self.face.setPos(xoffset, yoffset)
self.face.setSharedRenderer(self.tileset.renderer())
- else:
+ elif self.face:
self.face = None
self.setTileId()
board = property(getBoard, setBoard)
+
+ def getFaceDown(self):
+ """does the tile with face down?"""
+ return self.__faceDown
+
+ def setFaceDown(self, faceDown):
+ """turn the tile face up/down"""
+ self.__faceDown = faceDown
+ self.recompute()
+
+ faceDown = property(getFaceDown, setFaceDown)
+ def setPos(self, xoffset=0, yoffset=0, level=0):
+ """change Position of tile in board"""
+ self.level = level
+ self.xoffset = xoffset
+ self.yoffset = yoffset
+ self.board.setDrawingOrder()
+ self.recompute()
+
def setTileId(self):
"""sets the SVG element id of the tile"""
lightSourceIndex = LIGHTSOURCES.index(self.board.rotatedLightSource())
@@ -143,14 +176,13 @@
shiftZ = self.board.shiftZ(self.level)
sceneX = self.xoffset*width+ shiftZ.x()
sceneY = self.yoffset*height+ shiftZ.y()
- self.setPos(sceneX, sceneY)
+ QGraphicsRectItem.setPos(self, sceneX, sceneY)
def select(self, selected=True):
"""selected tiles are drawn differently"""
if self.selected != selected:
self.selected = selected
self.setTileId()
-
class PlayerWind(QGraphicsEllipseItem):
"""a round wind tile"""
@@ -230,11 +262,11 @@
result += rect.top()
return result
- def addTile(self, element, xoffset = 0, yoffset = 0, level=0):
+ def addTile(self, element, xoffset = 0, yoffset = 0, level=0, faceDown=False):
"""adds a new tile to the board. If a tile with the same size exists at this
position, change that existing tile and return the existing tile. If a
tile exists with the same topleft position, we delete that one first"""
- tile = Tile(element, xoffset, yoffset, level=level)
+ tile = Tile(element, xoffset, yoffset, level=level, faceDown=faceDown)
tile.board = self
self.setDrawingOrder()
return tile
@@ -373,22 +405,30 @@
item.placeInScene()
return
- def allTiles(self):
- """returns a list with all tileface names"""
+ def getAllTiles(self):
+ """returns a randomized list with all tileface names,
+ This list will be built only if it does not yet exist. If you want it to
+ be rebuilt with new random values, use flushAllTiles"""
if len(self.__allTiles) == 0:
for name, num, amount in (('CHARACTER', 9, 4), ('BAMBOO', 9, 4),
('ROD', 9, 4), ('SEASON', 4, 1), ('FLOWER', 4, 1), ('WIND', 4, 4),
('DRAGON', 3, 4)):
for idx in range(1, num+1):
self.__allTiles.extend([name + '_' + str(idx)]*amount)
- return list(self.__allTiles)
+ random.shuffle(self.__allTiles)
+ return self.__allTiles
+ allTiles = property(getAllTiles)
+
+ def flushAllTiles(self):
+ """throw away the random tile list. Next access to allTiles will rebuild it"""
+ self.__allTiles = []
+
def randomTile144(self):
"""a generator returning 144 random tiles"""
- tiles = self.allTiles()
- random.shuffle(tiles)
- for idx in range(0, len(tiles)):
- yield tiles[idx]
+ self.flushAllTiles()
+ for idx in range(0, len(self.allTiles)):
+ yield self.allTiles[idx]
class FittingView(QGraphicsView):
@@ -424,15 +464,19 @@
def __init__(self, length, tileset):
Board.__init__(self)
self.length = length
- self.dividePos = None
self.lightSource = 'NW'
self.tileset = tileset
- self.walls = [self.wall(angle) for angle in (270, 0, 90, 180)]
- self.walls[0].setPos(xWidth=self.length, yWidth=self.length, yHeight=1 )
- self.walls[1].setPos(yWidth=self.length)
- self.walls[2].setPos(xHeight=1)
- self.walls[3].setPos(xHeight=1, xWidth=self.length, yHeight=1)
+ self.tile = self.randomTile144()
+ self.tiles = []
+ # living end: self.tiles[0]
+ # dead end: self.tiles[-1]
+ self.walls = [self.wall(angle) for angle in (0, 90, 180, 270)]
+ self.walls[0].setPos(yWidth=self.length)
+ self.walls[1].setPos(xHeight=1)
+ self.walls[2].setPos(xHeight=1, xWidth=self.length, yHeight=1)
+ self.walls[3].setPos(xWidth=self.length, yWidth=self.length, yHeight=1 )
self.setDrawingOrder()
+ self.divide(0, 4)
def __getitem__(self, index):
return self.walls[index]
@@ -442,11 +486,29 @@
result = Board(rotation)
result.setParentItem(self)
result.lightSource = self.lightSource
- for position in range(0, self.length):
- result.addTile('', position)
- result.addTile('', position, level=1)
+ for position in range(self.length-1, -1, -1):
+ self.tiles.append(result.addTile(self.tile.next(), position, level=1, faceDown=True))
+ self.tiles.append(result.addTile(self.tile.next(), position, faceDown=True))
return result
+
+ def moveDividedTile(self, angle, tile, offset):
+ """moves a tile from the divide hole to its new place"""
+ newOffset = tile.xoffset + offset
+ if newOffset >= self.length:
+ tile.board = self.walls[(angle//90+3) % 4]
+ tile.setPos(newOffset % self.length, level=2)
+ def divide(self, angle, diceSum):
+ """divides the wall with angle, building a living and and a dead end"""
+ livingEnd = angle//90 * self.length + diceSum*2
+ # shift tiles: tile[0] becomes living end
+ self.tiles = self.tiles[livingEnd:] + self.tiles[0:livingEnd]
+ # move last two tiles onto the dead end:
+ self.moveDividedTile(angle, self.tiles[-1], 3)
+ self.moveDividedTile(angle, self.tiles[-2], 5)
+ self.tiles = self.tiles[:-12] + self.tiles[-2:-1] + self.tiles[-12:-8] + \
+ self.tiles[-1:] + self.tiles[-8:-2]
+
class Shisen(Board):
"""builds a Shisen board, just for testing"""
def __init__(self):
--- trunk/playground/games/kmj/kmj.py #932373:932374
@@ -528,8 +528,8 @@
"""sets the background of the central widget"""
if not self.background:
self.background = Background(self.pref.background)
- self.background.setPalette(self.centralWidget)
- self.centralWidget.setAutoFillBackground(True)
+ self.background.setPalette(self.centralWidget())
+ self.centralWidget().setAutoFillBackground(True)
def resizeEvent(self, event):
"""adapt background to new window size"""
@@ -544,10 +544,10 @@
for a huge rect like 4000x3000 where my screen only has
1920x1200"""
self.setObjectName("MainWindow")
- self.centralWidget = QWidget()
+ centralWidget = QWidget()
self.centralScene = QGraphicsScene()
self.centralView = FittingView()
- layout = QGridLayout(self.centralWidget)
+ layout = QGridLayout(centralWidget)
layout.setContentsMargins(0, 0, 0, 0)
layout.addWidget(self.centralView)
self.centralView.setScene(self.centralScene)
@@ -562,7 +562,7 @@
for player in self.players:
player.wind.setTileset(self.windTileset)
- self.setCentralWidget(self.centralWidget)
+ self.setCentralWidget(centralWidget)
self.actionNewGame = self.kmjAction("new", "document-new", self.newGame)
self.actionPlayers = self.kmjAction("players", "personal", self.slotPlayers)
self.actionNewHand = self.kmjAction("newhand", "object-rotate-left", self.newHand)
@@ -634,8 +634,7 @@
tileset from the config dialog is only applied the first time. It always
works if we ensure that the Tileset class gets a string with a
different id. Maybe there is a problem in the interaction between
- python strings and QString.
- TODO: I should really find out if this is a bug in my code or in pyqt"""
+ python strings and QString."""
if self.tileset.desktopFileName != self.pref.tileset:
self.tileset = Tileset(self.pref.tileset+'x'[:-1])
self.walls.tileset = self.tileset
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic