Génération du pdf à partir de la base de données
This commit is contained in:
parent
8fb934076d
commit
6f888390e4
|
@ -0,0 +1,21 @@
|
|||
# Generated by Django 5.0.4 on 2024-04-15 00:12
|
||||
|
||||
from django.db import migrations
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('colloscope', '0001_initial'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterModelOptions(
|
||||
name='periode',
|
||||
options={'ordering': ['debut']},
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name='appartenance',
|
||||
name='periode',
|
||||
),
|
||||
]
|
|
@ -0,0 +1,17 @@
|
|||
# Generated by Django 5.0.4 on 2024-04-15 00:14
|
||||
|
||||
from django.db import migrations
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('colloscope', '0002_alter_periode_options_remove_appartenance_periode'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.RemoveField(
|
||||
model_name='creneau',
|
||||
name='classe',
|
||||
),
|
||||
]
|
|
@ -0,0 +1,20 @@
|
|||
# Generated by Django 5.0.4 on 2024-04-15 00:17
|
||||
|
||||
import django.db.models.deletion
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('colloscope', '0003_remove_creneau_classe'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AddField(
|
||||
model_name='matiere',
|
||||
name='classe',
|
||||
field=models.ForeignKey(default=1, on_delete=django.db.models.deletion.CASCADE, to='colloscope.classe'),
|
||||
preserve_default=False,
|
||||
),
|
||||
]
|
|
@ -1,5 +1,17 @@
|
|||
from math import ceil
|
||||
from datetime import date, datetime, timedelta
|
||||
|
||||
from django.db import models
|
||||
from django.db.models import F
|
||||
from django.db.models import F, Q
|
||||
|
||||
calendrier = {
|
||||
"C" : [
|
||||
( date(2023, 10, 21), date(2023, 11, 6) ),
|
||||
( date(2023, 12, 23), date(2024, 1, 8) ),
|
||||
( date(2024, 2, 10), date(2024, 2, 26) ),
|
||||
( date(2024, 4, 6), date(2024, 4, 22) ),
|
||||
]
|
||||
}
|
||||
|
||||
class Lycee(models.Model):
|
||||
uai = models.CharField(max_length=10)
|
||||
|
@ -19,7 +31,40 @@ class Periode(models.Model):
|
|||
debut = models.DateField()
|
||||
fin = models.DateField()
|
||||
|
||||
class Meta:
|
||||
ordering = ["debut"]
|
||||
|
||||
|
||||
def no_semaine(self, jour):
|
||||
zone = self.classe.lycee.vacances
|
||||
vacances = calendrier[zone]
|
||||
jour0 = self.classe.jour_zero
|
||||
|
||||
n = 1 + ((jour - jour0).days)//7
|
||||
for debut, fin in vacances:
|
||||
if jour > debut:
|
||||
n -= 2
|
||||
return n
|
||||
|
||||
def range_semaines(self):
|
||||
return range(self.no_semaine(self.debut), self.no_semaine(self.fin)+1)
|
||||
|
||||
def date_debut_sem(self, n):
|
||||
zone = self.classe.lycee.vacances
|
||||
vacances = calendrier[zone]
|
||||
jour0 = self.classe.jour_zero
|
||||
|
||||
jour = jour0 + (n-1) * timedelta(weeks=1)
|
||||
|
||||
for debut, _ in vacances:
|
||||
if jour >= debut:
|
||||
jour += 2*timedelta(weeks=1)
|
||||
|
||||
return jour
|
||||
|
||||
|
||||
class Matiere(models.Model):
|
||||
classe = models.ForeignKey(Classe, on_delete=models.CASCADE)
|
||||
libelle = models.CharField(max_length=100)
|
||||
code = models.CharField(max_length=20)
|
||||
|
||||
|
@ -35,6 +80,9 @@ class Groupe(models.Model):
|
|||
critere = models.ForeignKey(Critere, null=True, on_delete=models.CASCADE)
|
||||
libelle = models.CharField(max_length=100)
|
||||
|
||||
def membres(self):
|
||||
return Etudiant.objects.filter(id__in=Appartenance.objects.filter(groupe=self))
|
||||
|
||||
class Etudiant(models.Model):
|
||||
class Meta:
|
||||
ordering=["classe", "nom", "prenom"]
|
||||
|
@ -46,19 +94,18 @@ class Etudiant(models.Model):
|
|||
#lv2 = models.ForeignKey(Matiere, on_delete=models.CASCADE)
|
||||
|
||||
def appartient(self, groupe, periode):
|
||||
return Appartenance.objects.filter(periode=periode, etudiant=self, groupe=groupe).exists()
|
||||
return Appartenance.objects.filter(etudiant=self, groupe=groupe).exists()
|
||||
|
||||
def groupe_du_critere(self, periode, critere):
|
||||
if isinstance(critere, str):
|
||||
critere = Critere.objects.get(periode=periode, libelle=critere)
|
||||
|
||||
return Appartenance.objects.get(periode=periode, etudiant=self, groupe__critere=critere).groupe
|
||||
return Appartenance.objects.get(groupe__periode=periode, etudiant=self, groupe__critere=critere).groupe
|
||||
|
||||
def groupe_de_colle(self, periode):
|
||||
return self.groupe_du_critere(periode, "colle")
|
||||
|
||||
class Appartenance(models.Model):
|
||||
periode = models.ForeignKey(Periode, on_delete=models.CASCADE)
|
||||
etudiant = models.ForeignKey(Etudiant, on_delete=models.CASCADE)
|
||||
groupe = models.ForeignKey(Groupe, on_delete=models.CASCADE)
|
||||
|
||||
|
@ -67,12 +114,11 @@ class Colleur(models.Model):
|
|||
nom = models.CharField(max_length=100)
|
||||
|
||||
class Creneau(models.Model):
|
||||
classe = models.ForeignKey(Classe, on_delete=models.CASCADE)
|
||||
periode = models.ForeignKey(Periode, on_delete=models.CASCADE)
|
||||
jour = models.IntegerField()
|
||||
heure = models.TimeField()
|
||||
duree = models.DurationField()
|
||||
salle = models.CharField(max_length=20)
|
||||
periode = models.ForeignKey(Periode, on_delete=models.CASCADE)
|
||||
matiere = models.ForeignKey(Matiere, on_delete=models.CASCADE)
|
||||
colleur = models.ForeignKey(Colleur, on_delete=models.CASCADE)
|
||||
est_colle = models.BooleanField()
|
||||
|
@ -83,6 +129,21 @@ class Rotation(models.Model):
|
|||
groupes = models.ManyToManyField(Groupe)
|
||||
semaine = models.IntegerField()
|
||||
|
||||
def effectif(self):
|
||||
n_base = sum(len(groupe.membres()) for groupe in self.groupes.all())
|
||||
n_plus = len(Amendement.objects.filter(est_positif=True, rotation=self))
|
||||
n_moins = len(Amendement.objects.filter(est_positif=False, rotation=self))
|
||||
|
||||
return n_base + n_plus - n_moins
|
||||
|
||||
def est_pleine(self):
|
||||
eff = self.effectif()
|
||||
|
||||
if eff>self.creneau.capacite:
|
||||
raise models.IntegrityError
|
||||
else:
|
||||
return eff==self.creneau.capacite
|
||||
|
||||
class Amendement(models.Model):
|
||||
est_positif = models.BooleanField()
|
||||
rotation = models.ForeignKey(Rotation, on_delete=models.CASCADE)
|
||||
|
|
|
@ -1,29 +1,11 @@
|
|||
from datetime import date, timedelta
|
||||
|
||||
from colloscope.models import Etudiant, Critere, Classe
|
||||
from colloscope.models import Etudiant, Critere, Classe, Rotation, Periode, Creneau
|
||||
|
||||
from fpdf import FPDF
|
||||
from fpdf.fonts import FontFace
|
||||
from fpdf.enums import TableCellFillMode
|
||||
|
||||
calendrier_zoneC = date(2023, 9, 18), [
|
||||
( date(2023, 10, 21), date(2023, 11, 6) ),
|
||||
( date(2023, 12, 23), date(2024, 1, 8) ),
|
||||
( date(2024, 2, 10), date(2024, 2, 26) ),
|
||||
( date(2024, 4, 6), date(2024, 4, 22) ),
|
||||
]
|
||||
|
||||
def jour_of_sem(n, cal):
|
||||
sem_1, vac = cal
|
||||
|
||||
jour = sem_1 + (n-1) * timedelta(weeks=1)
|
||||
|
||||
for (debut, fin) in vac:
|
||||
if jour >= debut:
|
||||
jour += 2*timedelta(weeks=1)
|
||||
|
||||
return jour
|
||||
|
||||
"""
|
||||
etudiants = [
|
||||
['Aboujaib', 'Alexandre', 4, 'A', '', ''],
|
||||
|
@ -124,7 +106,12 @@ class PDF(FPDF):
|
|||
row.cell("??") # LV2
|
||||
|
||||
|
||||
def table_colloscope(self, creneaux, semaines, rotations):
|
||||
def table_colloscope(self, periode):
|
||||
semaines = periode.range_semaines()
|
||||
lundis = [ periode.date_debut_sem(n) for n in semaines ]
|
||||
creneaux = Creneau.objects.filter(periode=periode)
|
||||
jours = ["dimanche", "lundi", "mardi", "mercredi", "jeudi", "vendredi", "samedi"]
|
||||
|
||||
with self.table(
|
||||
align="LEFT",
|
||||
width=190,
|
||||
|
@ -140,24 +127,29 @@ class PDF(FPDF):
|
|||
header.cell(str(sem), align="CENTER")
|
||||
|
||||
header2 = table.row()
|
||||
for sem in semaines:
|
||||
header2.cell(jour_of_sem(sem, calendrier_zoneC).strftime("%d/%m/%y"), align="CENTER")
|
||||
for lundi in lundis:
|
||||
header2.cell(lundi.strftime("%d/%m/%y"), align="CENTER")
|
||||
|
||||
for i, tr in enumerate(creneaux):
|
||||
matiere, jour, heure, colleur, salle = tr
|
||||
|
||||
for i, c in enumerate(creneaux):
|
||||
matiere = c.matiere
|
||||
jour = c.jour
|
||||
heure = c.heure
|
||||
colleur = c.colleur
|
||||
salle = c.salle
|
||||
|
||||
row = table.row()
|
||||
row.cell(matiere)
|
||||
row.cell(jour)
|
||||
row.cell(heure)
|
||||
row.cell(colleur)
|
||||
row.cell(matiere.libelle)
|
||||
row.cell(jours[jour])
|
||||
row.cell(heure.strftime("%H:%M"))
|
||||
row.cell("{} {}".format("M." if colleur.civilite=="M" else "Mme", colleur.nom.upper()))
|
||||
row.cell(salle)
|
||||
|
||||
for s in semaines:
|
||||
for rot in rotations:
|
||||
if rot[2] == i and rot[0] == s:
|
||||
row.cell(str(rot[1]), align="CENTER")
|
||||
break
|
||||
if Rotation.objects.filter(creneau=c, semaine=s).exists():
|
||||
rot = Rotation.objects.get(creneau=c, semaine=s)
|
||||
groupes = rot.groupes
|
||||
row.cell(", ".join(g.libelle for g in groupes.all()), align="CENTER")
|
||||
else:
|
||||
row.cell()
|
||||
|
||||
|
@ -195,8 +187,8 @@ def generate(periode):
|
|||
base_y = pdf.t_margin + 10
|
||||
pdf.set_y(base_y)
|
||||
pdf.liste_eleves(periode)
|
||||
#pdf.set_y(base_y)
|
||||
#pdf.table_colloscope(creneaux, semaines, rotations)
|
||||
pdf.set_y(base_y)
|
||||
pdf.table_colloscope(periode)
|
||||
#pdf.y += 3
|
||||
#pdf.table_travaux()
|
||||
|
||||
|
|
Loading…
Reference in New Issue