#from __future__ import unicode_literals # -*- coding: utf-8 -*- from __future__ import division import os from PyQt4.QtCore import * from PyQt4.QtGui import * from Pion import ImgPion, EtiquettePion class VueEditionForme(QGraphicsScene): """vue graphique permettant d'afficher et de modifier la forme des creatures/decors""" def __init__(self, fenetre, formeCases = "H", parent=None): super(VueEditionForme, self).__init__() self.fenetre = fenetre self._vefImage = VefImage(self) self._vefEtiquette = VefEtiquette(self) self._couleur = QColor("grey") self._cases = {} self._formeCases = formeCases self._l0 = 0 self._h0 = 0 self._rotation = 0 #acces aux donnees def vue(self): """retourne la ref de la QGraphicsView""" return self.fenetre.ui.vueForme def chargerFormeDef(self, formeDef): self._formeDef = formeDef self._majFormeGraphique() def formeDef(self): """renvoie la definition de forme (selon la forme des cases actuelle)""" retour = [] for coord in self._cases: if self._cases[coord].estSelectionnee and coord != (0,0): retour.append(coord) return retour def chargerEtiquetteDef(self, etiquetteDef): ## self._majEtiquette(txt) self._vefEtiquette.charger(etiquetteDef) def etiquetteDef(self): return self._etiquette def chargerImageDef(self, imgDef): ## self._majImage(sourceImg) self._vefImage.charger(imgDef) def imageDef(self): return self._img def majCouleur(self, couleur): """met a jour la couleur du pion""" self._couleur = couleur self._majCouleurGraphique() def couleur(self): return self._couleur def formeCases(self): return self._formeCases #creation, suppression, mises a jour... def creer(self): for x in range(-5,6): for y in range(-5,6): if self._formeCases == "H": if 1 == (x % 2): y += 0.5 c = CaseEditionForme(self) c.creer(x, y, self._formeCases) self.cases[(x,y)] = c self.vue().setScene(self) self.vue().centerOn(self.vue().mapFromScene(QPointF(60,60))) #centre la vue sur la case 0,0 self.vue().scale(0.25, 0.25) def vider(self): for coord in self._cases: self.removeItem(self._cases[coord]) def _majFormeGraphique(self): """met a jour la forme affichee sur le graphique""" if self._formeDef: for coord in self._formeDef: if coord in self._cases: self._cases[coord].estSelectionnee = True self._cases[coord].setBrush(self._couleur) ## def _majEtiquette(self, txt, taillePolice = 20, gras = False, dx = 0, dy = 0, rotation = 0): ## if len(txt) > 0: ## if not self._etiquette: ## self._etiquette = QGraphicsSimpleTextItem() ## self.addItem(self._etiquette) ## self._etiquette.setText(QString.fromUtf8("1."+txt)) ## self._etiquette.setPos(QPointF(dx-0.112*120, dy-0.275*120)) ## police = QFont("Georgia", taillePolice) ## police.setBold(gras) ## self._etiquette.setFont(police) ## self._etiquette.setRotation(rotation) ## ## else: ## if self._etiquette: ## self.removeItem(self._etiquette) ## def _majImage(self, img, kx = 10, ky = 10, dx = 0, dy = 0, rotation = 0): ## ## if len(img) > 0: ## pix = QPixmap(QString.fromUtf8("img\\"+img)) ## if not pix.isNull(): ## ## if not self._imgGraphique: ## self._imgGraphique = QGraphicsPixmapItem() ## self.addItem(self._imgGraphique) ## self._imgGraphique.setZValue(10) ## ## if pix.height() >= pix.width(): ## pix = pix.scaledToHeight(120*0.9, Qt.SmoothTransformation) ## else: ## pix = pix.scaledToWidth(120*0.9, Qt.SmoothTransformation) ## self.largeurOriginale = pix.width() ## self.hauteurOriginale = pix.height() ## ## pix = pix.scaled((kx/10)*self.l0, (ky/10)*self.h0, Qt.IgnoreAspectRatio, Qt.SmoothTransformation) ## deltaX = dx + 0.5*(120*1.1544 - self.l0) ## deltaY = dy + 0.5*(120 - self.h0) ## ## self._imgGraphique.setPixmap(pix) ## self._imgGraphique.setPos(QPointF(deltaX, deltaY)) ## self._imgGraphique.setRotation(rotation) ## else: ## if self._imgGraphique: ## self.removeItem(self._imgGraphique) def majSelection(self, coord): """met a jour l'affichage des cases selectionnees pour l'affichage de la forme""" if self.cases[coord].estSelectionnee == True: self.cases[coord].estSelectionnee = False valide = True for coordVerif in self.cases: #on parcourt les autres cases selectionnees if coordVerif != (0,0) and coordVerif != coord and self.cases[coordVerif].estSelectionnee == True: #on liste les cases connectees a cette case, de proche en proche connectees = [coordVerif] for coordVerif2 in connectees: for coordVoisin in self.cases[coordVerif2].voisins: if coordVoisin in self.cases and not coordVoisin in connectees: if self.cases[coordVoisin].estSelectionnee: connectees.append(coordVoisin) if not (0,0) in connectees: valide = False break if valide == True: self.cases[coord].setBrush(QColor("white")) else: self.cases[coord].estSelectionnee = True else: #on s'assure que la case est bien adjacente a une case selectionnee valide = False for coordVerif in self.cases[coord].voisins: if coordVerif in self.cases: if self.cases[coordVerif].estSelectionnee == True: valide = True break if valide: self.cases[coord].estSelectionnee = True self.cases[coord].setBrush(QColor("red")) class VefCase(QGraphicsPolygonItem): """case utilisee dans une VueEditionForme()""" def __init__(self, scene, parent=None): super(CaseEditionForme, self).__init__() self.scene = scene self._position = (0,0) self._estSelectionnee = False self._voisins = [] #interactions graphiques self.setFlag(QGraphicsItem.ItemIsFocusable) self.setAcceptHoverEvents(True) def estSelectionnee(self): return self._estSelectionnee def creer(self, x, y, couleur, formeCases="H"): """creation du polygone et enregistrement des donnees geometriques""" self._position = (x, y) polygone = QPolygonF() if self.scene.formeCases == "H": polygone << QPointF(((x*0.866)+0.2886)*120, y*120) \ << QPointF(((x*0.866)+0.866)*120, y*120) \ << QPointF(((x*0.866)+1.1547)*120, (y+0.5)*120) \ << QPointF(((x*0.866)+0.866)*120, (y+1)*120) \ << QPointF(((x*0.866)+0.2886)*120, (y+1)*120) \ << QPointF( (x*0.866)*120, (y+0.5)*120) else: polygone << QPointF(x*120, y*120) \ << QPointF((x+1)*120, y*120) \ << QPointF((x+1)*120, (y+1)*120) \ << QPointF(x*120, (y+1)*120) self.setPolygon(polygone) #enregistrement des cases voisines: if self.scene.formeCases() == "H": self.voisins.append((x, y+1)) self.voisins.append((x, y-1)) self.voisins.append((x-1, y+0.5)) self.voisins.append((x-1, y-0.5)) self.voisins.append((x+1, y+0.5)) self.voisins.append((x+1, y-0.5)) else: self.voisins.append((x, y-1)) self.voisins.append((x, y+1)) self.voisins.append((x-1, y)) self.voisins.append((x+1, y)) #pour afficher les coordonnees des cases: #text = QGraphicsSimpleTextItem("{}-{}".format(x,y), parent=self) #police = QFont() #police.setPointSize(20) #text.setFont(police) #text.setPos(QPointF(((x*0.866)+0.2886)*120, y*120)) #couleur de fond par defaut if couleur.__class__.__name__ == "QColor": if not couleur.isValid(): couleur = QColor("grey") else: couleur = QColor("grey") if self._position == (0, 0): couleur.darker(150) self.setBrush(couleur) self.estSelectionnee = True else: self.setBrush(QColor(255,255,255,50)) #creation de l'objet graphique sur le plateau self.scene.addItem(self) def mousePressEvent(self, event): """evenement lors du clic souris""" super(CaseEditionForme, self).mousePressEvent(event) if event.button() == 1: #sur clic gauche if self._position != (0, 0): self.scene.majSelection(self._position) class VefImage(QGraphicsPixmapItem): """etiquette utilisee dans une VueEditionForme()""" def __init__(self, scene, parent=None): super(VefEtiquette, self).__init__() self.scene = scene self._def = ImgPion() self._pix = None self._l0 = 0 self._h0 = 0 self.setFlags(QGraphicsItem.ItemIsMovable | QGraphicsItem.ItemIsSelectable | \ QGraphicsItem.ItemSendsGeometryChanges | QGraphicsItem.ItemIsFocusable) def charger(self, definition): self._pix = None self._l0 = 0 self._h0 = 0 self._def = definition self.scene.addItem(self) self.setZValue(10) self.maj() def definition(self): return self._def def _maj(self): if self._pix == None: if len(self._def.nomFichier) > 0: self._pix = QPixmap(QString.fromUtf8(self._def.nomFichier)) if not self._pix.isNull(): if self._pix.height() >= self._pix.width(): self._pix = self._pix.scaledToHeight(120*0.9, Qt.SmoothTransformation) else: self._pix = self._pix.scaledToWidth(120*0.9, Qt.SmoothTransformation) self.l0 = self._pix.width() self.h0 = self._pix.height() else: self._pix = None if self._pix: self._pix = self._pix.scaled((self._def.kx/10)*self._l0, (self._def.ky/10)*self._h0, \ Qt.IgnoreAspectRatio, Qt.SmoothTransformation) deltaX = self._def.dx + 0.5*(120*1.1544 - self._l0) deltaY = self._def.dy + 0.5*(120 - self._h0) self.setPixmap(self._pix) self.setPos(QPointF(deltaX, deltaY)) self.setRotation(self._def.rotation) ## def mousePressEvent(self, event): ## pass class VefEtiquette(QGraphicsTextItem): """etiquette utilisee dans une VueEditionForme()""" def __init__(self, scene, parent=None): super(VefEtiquette, self).__init__() self.scene = scene self._def = EtiquettePion() self.setFlags(QGraphicsItem.ItemIsMovable | QGraphicsItem.ItemIsSelectable | \ QGraphicsItem.ItemSendsGeometryChanges | QGraphicsItem.ItemIsFocusable) def charger(self, definition): self._def = definition self.scene.addItem(self) self.setZValue(10) self.maj() def definition(self): return self._def def _maj(self): if len(self._def.txt) > 0: self.setText(QString.fromUtf8(self._def.txt)) self.setPos(QPointF(self._def.dx-0.112*120, self._def.dy-0.275*120)) police = QFont("Georgia", self._def.taillePolice) police.setBold(True) self.setFont(police)