Compare commits

..

1 Commits

Author SHA1 Message Date
cd14f05d54 Merge pull request 'simple' (#1) from simple into dev
Reviewed-on: #1
2025-02-13 10:32:13 +00:00
8 changed files with 84 additions and 609 deletions

View File

@@ -1,59 +1,11 @@
# Gestion des tournois
## Refactored
## Introduction
All models are in `models/models.py`
Sequence can be seen in `controllers/base.py` in the `Controller.run()` method
Ces instructions vous permettent de :
- récupérer le programme,
- d'installer l'environnement nécessaire à son exécution,
- de l'exécuter,
- de l'utiliser
for testing purpose, the players_list is created when controller is instantiated
### Pré-requis
```
paquets : python 3.11, python3.11-venv, git
```
### Installation
Voici les étapes à suivre pour avoir un environnement d'exécution opérationnel :
créer l'environnement virtuel
```
python3.11 -m venv env
source env/bin/activate
```
cloner le dépôt, aller dans le bon dossier
```
git clone https://mcstn.fr/gitea/Yann/Projet4.git
```
## Exécution
exécuter la commande :
```
python3 main.py
```
## Utilisation
Toutes les actions se font via le menu affiché.
Il y a deux menus : général et rapport.
Si vous souhaitez spécifier une liste de joueurs au format JSON, il vous faut la placer
dans le répertoire `data`
Sinon, vous pouvez créer des joueurs via le menu
Le répertoire, nom des fichiers joueurs et tournois sont des constantes de models.py
Ils sont placés dans le dossier `data`
## Auteur
Yann <yann@needsome.coffee>
## License
N/A
To test, execute the controllers/base.py
- first menu is called from view
- the method to create player just returns the object (doesn't write anything)
- 1 -> creates a new tournament then run it

View File

@@ -1,5 +1,8 @@
from models.models import (Player, Round, Match, MatchHistory)
from models.models import DATAPATH, PLAYERFILE, TOURNAMENTFILE
from ChessTournament.models.models import (Player, Tournament, Round, Match,
MatchHistory)
from ChessTournament.models.models import DATAPATH, PLAYERFILE, TOURNAMENTFILE
from ChessTournament.views.menu import Menu
from ChessTournament.views.base import View
from random import shuffle
import os
@@ -31,6 +34,7 @@ class Save:
json_file.write(json.dumps(data_tmp))
return "Done."
def player_write(self, player) -> bool:
data_tmp = []
if self.load_file(PLAYERFILE):
@@ -61,6 +65,8 @@ class Save:
data = {
tournament.name: tournament.data()
}
print(data)
if self.load_file(TOURNAMENTFILE):
data_tmp = self.load_file(TOURNAMENTFILE)
data_tmp[tournament.name] = tournament.data()
@@ -105,12 +111,13 @@ class Application:
self.tournament.players_list = self.save.player_load()
self.save.tournament_write(self.tournament)
else:
self.view.display_player_instructions()
print("Placez un fichier joueur dans le répertoire data"
"ou créez des nouveaux joueurs depuis le menu")
print()
self.menu_manager()
def run_tournament(self):
shuffle(self.tournament.players_list)
self.view.display_players(self.tournament.players_list)
for each_round in range(1, self.tournament.total_round + 1):
self.tournament.current_round += 1
self.round = Round()
@@ -120,7 +127,6 @@ class Application:
self.round.start_time = self.round.get_time()
# create matches TODO : check from history
self.round.match_list = self.create_match()
self.match_history.add(self.round.match_list)
# display matches
self.view.display_matches(self.round.match_list)
self.view.prompt_for_scores()
@@ -128,6 +134,7 @@ class Application:
self.scores(self.round.match_list)
self.sort_by_score()
self.tournament.round_list.append(self.round.save())
print("après maj", self.tournament.round_list)
self.save.tournament_write(self.tournament)
self.view.display_round_info(self.round)
self.view.display_scores(self.tournament.players_list)
@@ -158,15 +165,9 @@ class Application:
for i in range(0, len(self.tournament.players_list), 2):
j += 1
match = Match()
try:
match.player1 = self.tournament.players_list[i]
match.player2 = self.tournament.players_list[i+1]
if self.match_history.check(match):
# match.player2 = self.tournament.players_list[i+2]
print("deja joue")
match_list.append(match)
except IndexError:
pass
return match_list
def scores(self, match_list) -> list:
@@ -192,13 +193,14 @@ class Application:
matches.append(match.get_data())
return matches
def menu_manager(self):
menu_choice = self.menu.items(1)
while True:
# Quit
if menu_choice == "4":
print("Bye")
break
# Rapports
elif menu_choice == "3":
rapport_choice = self.menu.items(2)
@@ -216,8 +218,7 @@ class Application:
# Display list of tournaments
elif rapport_choice == "2":
if self.save.tournament_load():
self.view.display_tournaments(
self.save.tournament_load())
self.view.display_tournaments(self.save.tournament_load())
input("?")
# display tournament's details
@@ -244,4 +245,25 @@ class Application:
print("c'est parti")
self.create_tournament()
self.run_tournament()
self.view.display_winner(self.tournament.players_list)
self.view.display_scores(self.tournament.players_list)
self.menu_manager()
class CheckMatch:
pass
class MenuManager:
pass
class TournamentManager:
def __init__(self):
pass
class UserManager:
pass

View File

@@ -1,73 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="32"
height="48"
viewBox="0 0 32 48"
id="svg2"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="back.svg">
<defs
id="defs4" />
<sodipodi:namedview
id="base"
pagecolor="#3d3d3d"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:zoom="4"
inkscape:cx="47.245066"
inkscape:cy="13.218734"
inkscape:document-units="px"
inkscape:current-layer="layer1"
showgrid="false"
units="px"
width="32px"
inkscape:window-width="1535"
inkscape:window-height="876"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="1" />
<metadata
id="metadata7">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title />
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(0,-1004.3622)">
<g
id="g5305"
transform="translate(0,-3.5)">
<path
inkscape:connector-curvature="0"
id="path5301"
d="M 15.577993,1039.1732 4.7040093,1028.3079 15.469253,1017.5512"
style="fill:none;fill-rule:evenodd;stroke:#ffffff;stroke-width:6;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
<path
inkscape:connector-curvature="0"
id="path5303"
d="m 4.921489,1028.3622 26.53252,0"
style="fill:none;fill-rule:evenodd;stroke:#ffffff;stroke-width:6;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
</g>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 2.2 KiB

View File

@@ -1,64 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="32"
height="48"
viewBox="0 0 32 48"
id="svg2"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="file.svg">
<defs
id="defs4" />
<sodipodi:namedview
id="base"
pagecolor="#3d3d3d"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:zoom="1"
inkscape:cx="24.812518"
inkscape:cy="18.901073"
inkscape:document-units="px"
inkscape:current-layer="layer1"
showgrid="false"
units="px"
width="32px"
inkscape:window-width="1535"
inkscape:window-height="876"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="1" />
<metadata
id="metadata7">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(0,-1004.3622)">
<path
style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate"
d="m 4.1360619,1007.3622 0,34.375 23.7278761,0 0,-29.9038 -4.471158,-4.4712 -19.2567181,0 z m 18.5469091,0.6084 4.471159,4.4712 -4.471159,0 0,-4.4712 z m -16.6202866,7.8079 19.8746316,0 0,1.8252 -19.8746316,0 0,-1.8252 z m 0,3.2448 19.8746316,0 0,1.8253 -19.8746316,0 0,-1.8253 z m 0,6.0841 19.8746316,0 0,1.8252 -19.8746316,0 0,-1.8252 z m 0,8.2135 19.8746316,0 0,1.8252 -19.8746316,0 0,-1.8252 z"
id="path4749"
inkscape:connector-curvature="0" />
</g>
</svg>

Before

Width:  |  Height:  |  Size: 2.6 KiB

View File

@@ -1,30 +0,0 @@
<!DOCTYPE html>
<html>
<head>
<title>flake8 violations</title>
<meta http-equiv="Content-Type" value="text/html; charset=UTF-8">
<link rel="stylesheet" href="styles.css">
</head>
<body>
<div id="masthead" class="sev-4"></div>
<div id="page">
<h1>flake8 violations</h1>
<p id="versions">Generated on 2025-02-13 15:45
with Installed plugins: flake8-html: 0.4.3, mccabe: 0.7.0, pycodestyle: 2.12.1, pyflakes: 3.2.0
</p>
<ul id="index">
<li>
<div id="all-good">
<span class="count sev-4">
<span class="tick">&#x2713;</span>
</span>
<h2>All good!</h2>
<p>No flake8 errors found in 8 files scanned.</p>
</div>
</li>
</ul>
</div>
</body>
</html>

View File

@@ -1,327 +0,0 @@
html {
font-family: sans-serif;
font-size: 90%;
}
#masthead {
position: fixed;
left: 0;
top: 0;
right: 0;
height: 40%;
}
h1, h2 {
font-family: sans-serif;
font-weight: normal;
}
h1 {
color: white;
font-size: 36px;
margin-top: 1em;
}
h1 img {
margin-right: 0.3em;
}
h2 {
margin-top: 0;
}
h1 a {
color: white;
}
#versions {
color: rgba(255, 255, 255, 0.7);
}
#page {
position: relative;
max-width: 960px;
margin: 0 auto;
}
#index {
background-color: white;
box-shadow: 0 0 4px rgba(0, 0, 0, 0.8);
padding: 0;
margin: 0;
}
#index li {
list-style: none;
margin: 0;
padding: 1px 0;
}
#index li + li {
border-top: solid silver 1px;
}
.details p {
margin-left: 3em;
color: #888;
}
#index a {
display: block;
padding: 0.8em 1em;
cursor: pointer;
}
#index #all-good {
padding: 1.4em 1em 0.8em;
}
#all-good .count .tick {
font-size: 2em;
}
#all-good .count {
float: left;
}
#all-good h2,
#all-good p {
margin-left: 50px;
}
#index a:hover {
background-color: #eee;
}
.count {
display: inline-block;
border-radius: 50%;
text-align: center;
width: 2.5em;
line-height: 2.5em;
height: 2.5em;
color: white;
margin-right: 1em;
}
.sev-1 {
background-color: #a00;
}
.sev-2 {
background-color: #b80;
}
.sev-3 {
background-color: #28c;
}
.sev-4 {
background-color: #383;
}
a {
text-decoration: none;
}
#doc {
background-color: white;
margin: 1em 0;
padding: 1em;
padding-left: 1.2em;
position: relative;
box-shadow: 0 0 4px rgba(0, 0, 0, 0.8);
}
#doc pre {
margin: 0;
padding: 0.07em;
}
.violations {
position: absolute;
margin: 1.2em 0 0 3em;
padding: 0.5em 1em;
font-size: 14px;
background-color: white;
box-shadow: 0 0 4px rgba(0, 0, 0, 0.4);
display: none;
}
.violations .count {
font-size: 70%;
}
.violations li {
padding: 0.1em 0.3em;
list-style: none;
}
.line-violations::before {
display: block;
content: "";
position: absolute;
left: -1em;
width: 14px;
height: 14px;
border-radius: 50%;
background-color: red;
}
.code:hover .violations {
display: block;
}
tt {
white-space: pre-wrap;
font-family: Consolas, monospace;
font-size: 10pt;
}
tt i {
color: silver;
display: inline-block;
text-align: right;
width: 3em;
box-sizing: border-box;
height: 100%;
border-right: solid #eee 1px;
padding-right: 0.2em;
}
.le {
background-color: #ffe8e8;
cursor: pointer;
}
.le:hover {
background-color: #fcc;
}
.details {
clear: both;
}
#index .details {
border-top-style: none;
margin: 1em;
}
ul.details {
margin-left: 0;
padding-left: 0;
}
#index .details li {
list-style: none;
border-top-style: none;
margin: 0.3em 0;
padding: 0;
}
#srclink {
float: right;
font-size: 36px;
margin: 0;
}
#srclink a {
color: white;
}
#index .details a {
padding: 0;
color: inherit;
}
.le {
background-color: #ffe8e8;
cursor: pointer;
}
.le.sev-1 {
background-color: #f88;
}
.le.sev-2 {
background-color: #fda;
}
.le.sev-3 {
background-color: #adf;
}
img {
height: 1.2em;
vertical-align: -0.35em;
}
pre { line-height: 125%; }
td.linenos .normal { color: inherit; background-color: transparent; padding-left: 5px; padding-right: 5px; }
span.linenos { color: inherit; background-color: transparent; padding-left: 5px; padding-right: 5px; }
td.linenos .special { color: #000000; background-color: #ffffc0; padding-left: 5px; padding-right: 5px; }
span.linenos.special { color: #000000; background-color: #ffffc0; padding-left: 5px; padding-right: 5px; }
.hll { background-color: #ffffcc }
.c { color: #3D7B7B; font-style: italic } /* Comment */
.err { border: 1px solid #F00 } /* Error */
.k { color: #008000; font-weight: bold } /* Keyword */
.o { color: #666 } /* Operator */
.ch { color: #3D7B7B; font-style: italic } /* Comment.Hashbang */
.cm { color: #3D7B7B; font-style: italic } /* Comment.Multiline */
.cp { color: #9C6500 } /* Comment.Preproc */
.cpf { color: #3D7B7B; font-style: italic } /* Comment.PreprocFile */
.c1 { color: #3D7B7B; font-style: italic } /* Comment.Single */
.cs { color: #3D7B7B; font-style: italic } /* Comment.Special */
.gd { color: #A00000 } /* Generic.Deleted */
.ge { font-style: italic } /* Generic.Emph */
.ges { font-weight: bold; font-style: italic } /* Generic.EmphStrong */
.gr { color: #E40000 } /* Generic.Error */
.gh { color: #000080; font-weight: bold } /* Generic.Heading */
.gi { color: #008400 } /* Generic.Inserted */
.go { color: #717171 } /* Generic.Output */
.gp { color: #000080; font-weight: bold } /* Generic.Prompt */
.gs { font-weight: bold } /* Generic.Strong */
.gu { color: #800080; font-weight: bold } /* Generic.Subheading */
.gt { color: #04D } /* Generic.Traceback */
.kc { color: #008000; font-weight: bold } /* Keyword.Constant */
.kd { color: #008000; font-weight: bold } /* Keyword.Declaration */
.kn { color: #008000; font-weight: bold } /* Keyword.Namespace */
.kp { color: #008000 } /* Keyword.Pseudo */
.kr { color: #008000; font-weight: bold } /* Keyword.Reserved */
.kt { color: #B00040 } /* Keyword.Type */
.m { color: #666 } /* Literal.Number */
.s { color: #BA2121 } /* Literal.String */
.na { color: #687822 } /* Name.Attribute */
.nb { color: #008000 } /* Name.Builtin */
.nc { color: #00F; font-weight: bold } /* Name.Class */
.no { color: #800 } /* Name.Constant */
.nd { color: #A2F } /* Name.Decorator */
.ni { color: #717171; font-weight: bold } /* Name.Entity */
.ne { color: #CB3F38; font-weight: bold } /* Name.Exception */
.nf { color: #00F } /* Name.Function */
.nl { color: #767600 } /* Name.Label */
.nn { color: #00F; font-weight: bold } /* Name.Namespace */
.nt { color: #008000; font-weight: bold } /* Name.Tag */
.nv { color: #19177C } /* Name.Variable */
.ow { color: #A2F; font-weight: bold } /* Operator.Word */
.w { color: #BBB } /* Text.Whitespace */
.mb { color: #666 } /* Literal.Number.Bin */
.mf { color: #666 } /* Literal.Number.Float */
.mh { color: #666 } /* Literal.Number.Hex */
.mi { color: #666 } /* Literal.Number.Integer */
.mo { color: #666 } /* Literal.Number.Oct */
.sa { color: #BA2121 } /* Literal.String.Affix */
.sb { color: #BA2121 } /* Literal.String.Backtick */
.sc { color: #BA2121 } /* Literal.String.Char */
.dl { color: #BA2121 } /* Literal.String.Delimiter */
.sd { color: #BA2121; font-style: italic } /* Literal.String.Doc */
.s2 { color: #BA2121 } /* Literal.String.Double */
.se { color: #AA5D1F; font-weight: bold } /* Literal.String.Escape */
.sh { color: #BA2121 } /* Literal.String.Heredoc */
.si { color: #A45A77; font-weight: bold } /* Literal.String.Interpol */
.sx { color: #008000 } /* Literal.String.Other */
.sr { color: #A45A77 } /* Literal.String.Regex */
.s1 { color: #BA2121 } /* Literal.String.Single */
.ss { color: #19177C } /* Literal.String.Symbol */
.bp { color: #008000 } /* Name.Builtin.Pseudo */
.fm { color: #00F } /* Name.Function.Magic */
.vc { color: #19177C } /* Name.Variable.Class */
.vg { color: #19177C } /* Name.Variable.Global */
.vi { color: #19177C } /* Name.Variable.Instance */
.vm { color: #19177C } /* Name.Variable.Magic */
.il { color: #666 } /* Literal.Number.Integer.Long */

View File

@@ -22,7 +22,6 @@ class Tournament:
self.round_list = []
self.current_round = 0
self.players_list = players_list
self.scores = []
self.description = "Pas de description"
def __str__(self):
@@ -68,8 +67,7 @@ class Player:
'prénom': self.name,
'nom': self.lastname,
'date de naissance': self.birthdate,
'ine': self.ine,
'score': self.score
'ine': self.ine
}
return player_dict

View File

@@ -34,6 +34,23 @@ class View:
input(f"Prêt à lancer le {round.name} ? (y)")
return True
def display_matches(self, match_list):
print("Liste des matchs : ")
for match in match_list:
print(match.player1.name, match.player1.lastname.upper(),
"contre", match.player2.name, match.player2.lastname.upper(),
"(", match, ")"
)
def display_round_info(self, round):
print("\n -> ", round)
def display_scores(self, players_list):
print("\nLes scores sont :")
print("-----------------")
for i in players_list:
print(i.ine, i.name, i.lastname, ":", i.score)
def prompt_for_new_player(self) -> dict:
print("Enregistrez un nouveau joueur :\n")
lastname = input("Nom de famille ? : ")
@@ -60,16 +77,6 @@ class View:
tournament_details['total_round'] = int(total_round)
return tournament_details
def prompt_tournament_to_display(self, tournament_list_to_display):
i = 0
temp_list = []
for tournament in tournament_list_to_display:
i += 1
print(i, ".", tournament)
temp_list.append(tournament)
num = int(input("Numéro du tournoi à afficher ? "))
return temp_list[num - 1]
def input_scores(self, match, count):
print("Scores pour le match", count, " :")
while True:
@@ -84,22 +91,13 @@ class View:
except ValueError:
print("Veuillez entrer un chiffre")
def display_matches(self, match_list):
print("Liste des matchs : ")
for match in match_list:
print(match.player1.name, match.player1.lastname.upper(),
"contre", match.player2.name, match.player2.lastname.upper(),
"(", match, ")"
)
def display_round_info(self, round):
print("\n -> ", round)
def display_scores(self, players_list):
print("\nLes scores sont :")
print("-----------------")
for i in players_list:
print(i.ine, ':', i.name, i.lastname, i.score)
def display_winner(self, player_list):
winner = max(player_list, key=lambda t: t.score)
print("Le gagnant est :",
winner.name,
winner.lastname,
"avec un score de :",
winner.score)
def display_players(self, player_list_to_display):
print("Liste des joueurs :")
@@ -113,16 +111,23 @@ class View:
"le",
tournament_list_to_display[tournament]['start'])
def prompt_tournament_to_display(self, tournament_list_to_display):
i = 0
temp_list = []
for tournament in tournament_list_to_display:
i += 1
print(i, ".", tournament)
temp_list.append(tournament)
num = int(input("Numéro du tournoi à afficher ? "))
return temp_list[num - 1]
def display_tournament_detail(self, tournament_to_display):
i = tournament_to_display
print("Nom du tournoi : ", i['name'])
print("Lieu : ", i['location'])
print("Description : ", i['description'])
print("Le tournoi a débuté le : ", i['start'])
print("Et s'est terminé le : ", i['end'])
print("\nLes participants étaient : ")
for j in i['players']:
print(j['ine'], "-", j['prénom'], str.upper(j['nom']))
print("Les participants étaient : \n", i['players'])
print("\nLes matches et leurs résultats étaient :")
for j in i['rounds']:
print(j['Nom'])
@@ -132,14 +137,6 @@ class View:
for k in j['Matches']:
print(k)
print()
print("Les scores finaux :")
for j in i['players']:
print(j['prénom'], str.upper(j['nom']), ":", j['score'])
def display_error(self):
print("Erreur de saisie, recommencez;")
def display_player_instructions(self):
print("Placez un fichier joueur dans le répertoire data "
"ou créez des nouveaux joueurs depuis le menu")
print()