forked from ScoDoc/DocScoDoc
Bul. BUT Bul: bookmarks, reportlab templates
This commit is contained in:
parent
dcc06d6169
commit
55c4f2c799
@ -24,6 +24,7 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
|
||||
list_in_menu = False # spécialisation du BulletinGeneratorStandard, ne pas présenter à l'utilisateur
|
||||
scale_table_in_page = False
|
||||
small_fontsize = "8"
|
||||
|
||||
def bul_table(self, format="html"):
|
||||
"""Génère la table centrale du bulletin de notes
|
||||
@ -77,16 +78,28 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
"coef": 2 * cm,
|
||||
}
|
||||
title_bg = tuple(x / 255.0 for x in title_bg)
|
||||
nota_bene = "La moyenne des ressources et SAÉs dans une UE dépend des poids donnés aux évaluations."
|
||||
# elems pour générer table avec gen_table (liste de dicts)
|
||||
rows = [
|
||||
# Ligne de titres
|
||||
{
|
||||
"titre": "Unités d'enseignement",
|
||||
"moyenne": "Note/20",
|
||||
"moyenne": Paragraph("<para align=right><b>Note/20</b></para>"),
|
||||
"coef": "Coef.",
|
||||
"_coef_pdf": Paragraph("<para align=right><b><i>Coef.</i></b></para>"),
|
||||
"_css_row_class": "note_bold",
|
||||
"_pdf_row_markup": ["b"],
|
||||
"_pdf_style": [
|
||||
("BACKGROUND", (0, 0), (-1, 0), title_bg),
|
||||
# ("BOTTOMPADDING", (0, 0), (-1, 0), 7),
|
||||
],
|
||||
},
|
||||
{
|
||||
"titre": nota_bene,
|
||||
"_titre_pdf": Paragraph(
|
||||
f"<para fontSize={self.small_fontsize}><i>{nota_bene}</i></para>"
|
||||
),
|
||||
"_titre_colspan": 3,
|
||||
"_pdf_style": [
|
||||
("BACKGROUND", (0, 0), (-1, 0), title_bg),
|
||||
("BOTTOMPADDING", (0, 0), (-1, 0), 7),
|
||||
@ -98,7 +111,7 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
blue,
|
||||
),
|
||||
],
|
||||
}
|
||||
},
|
||||
]
|
||||
col_keys = ["titre", "coef", "moyenne"] # noms des colonnes à afficher
|
||||
for ue_acronym, ue in self.infos["ues"].items():
|
||||
@ -106,7 +119,9 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
moy_ue = ue.get("moyenne")
|
||||
t = {
|
||||
"titre": f"{ue_acronym} - {ue['titre']}",
|
||||
"moyenne": moy_ue.get("value", "-") if moy_ue is not None else "-",
|
||||
"moyenne": Paragraph(
|
||||
f"""<para align=right><b>{moy_ue.get("value", "-") if moy_ue is not None else "-"}</b></para>"""
|
||||
),
|
||||
"_css_row_class": "note_bold",
|
||||
"_pdf_row_markup": ["b"],
|
||||
"_pdf_style": [
|
||||
@ -128,7 +143,7 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
"titre": f"""Bonus: {ue['bonus']} - Malus: {
|
||||
ue["malus"]}""",
|
||||
"coef": ects_txt,
|
||||
"_coef_pdf": Paragraph(f"""<para align=right>{ects_txt}</para>"""),
|
||||
"_coef_pdf": Paragraph(f"""<para align=left>{ects_txt}</para>"""),
|
||||
"_coef_colspan": 2,
|
||||
# "_css_row_class": "",
|
||||
# "_pdf_row_markup": [""],
|
||||
@ -157,7 +172,9 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
for mod_code, mod in ue[mod_type].items():
|
||||
t = {
|
||||
"titre": f"{mod_code} {self.infos[mod_type][mod_code]['titre']}",
|
||||
"moyenne": mod["moyenne"],
|
||||
"moyenne": Paragraph(
|
||||
f'<para align=right>{mod["moyenne"]}</para>'
|
||||
),
|
||||
"coef": mod["coef"],
|
||||
"_coef_pdf": Paragraph(
|
||||
f"<para align=right><i>{mod['coef']}</i></para>"
|
||||
@ -203,7 +220,6 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
- pdf_style : commandes table Platypus
|
||||
- largeurs de colonnes pour PDF
|
||||
"""
|
||||
poids_fontsize = "8"
|
||||
# UE à utiliser pour les poids (# colonne/UE)
|
||||
ue_acros = list(self.infos["ues"].keys()) # ['RT1.1', 'RT2.1', 'RT3.1']
|
||||
# Colonnes à afficher:
|
||||
@ -243,7 +259,7 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
}
|
||||
for ue_acro in ue_acros:
|
||||
t[ue_acro] = Paragraph(
|
||||
f"<para align=right fontSize={poids_fontsize}><i>{ue_acro}</i></para>"
|
||||
f"<para align=right fontSize={self.small_fontsize}><i>{ue_acro}</i></para>"
|
||||
)
|
||||
rows = [t]
|
||||
for mod_code, mod in self.infos[mod_type].items():
|
||||
@ -273,7 +289,7 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
"moyenne": e["note"]["value"],
|
||||
"coef": e["coef"],
|
||||
"_coef_pdf": Paragraph(
|
||||
f"<para align=right fontSize={poids_fontsize}><i>{e['coef']}</i></para>"
|
||||
f"<para align=right fontSize={self.small_fontsize}><i>{e['coef']}</i></para>"
|
||||
),
|
||||
"_pdf_style": [
|
||||
(
|
||||
@ -288,7 +304,7 @@ class BulletinGeneratorStandardBUT(BulletinGeneratorStandard):
|
||||
col_idx = 1 # 1ere col. poids
|
||||
for ue_acro in ue_acros:
|
||||
t[ue_acro] = Paragraph(
|
||||
f"""<para align=right fontSize={poids_fontsize}><i>{e["poids"].get(ue_acro, "")}</i></para>"""
|
||||
f"""<para align=right fontSize={self.small_fontsize}><i>{e["poids"].get(ue_acro, "") or ""}</i></para>"""
|
||||
)
|
||||
t["_pdf_style"].append(
|
||||
(
|
||||
|
@ -761,7 +761,7 @@ if __name__ == "__main__":
|
||||
doc = io.BytesIO()
|
||||
document = sco_pdf.BaseDocTemplate(doc)
|
||||
document.addPageTemplates(
|
||||
sco_pdf.ScolarsPageTemplate(
|
||||
sco_pdf.ScoDocPageTemplate(
|
||||
document,
|
||||
)
|
||||
)
|
||||
|
@ -154,9 +154,11 @@ class BulletinGenerator:
|
||||
from app.scodoc import sco_preferences
|
||||
|
||||
formsemestre_id = self.infos["formsemestre_id"]
|
||||
|
||||
objects = []
|
||||
# partie haute du bulletin
|
||||
objects = self.bul_title_pdf() # pylint: disable=no-member
|
||||
objects += self.bul_title_pdf() # pylint: disable=no-member
|
||||
objects += [sco_pdf.DebutBulletin(self.infos["etud"]["nomprenom"])]
|
||||
|
||||
# table des notes
|
||||
objects += self.bul_table(format="pdf") # pylint: disable=no-member
|
||||
# infos sous la table
|
||||
@ -168,6 +170,7 @@ class BulletinGenerator:
|
||||
# Réduit sur une page
|
||||
objects = [KeepInFrame(0, 0, objects, mode="shrink")]
|
||||
#
|
||||
# objects.append(sco_pdf.FinBulletin())
|
||||
if not stand_alone:
|
||||
objects.append(PageBreak()) # insert page break at end
|
||||
return objects
|
||||
@ -177,7 +180,7 @@ class BulletinGenerator:
|
||||
report = io.BytesIO() # in-memory document, no disk file
|
||||
document = sco_pdf.BaseDocTemplate(report)
|
||||
document.addPageTemplates(
|
||||
sco_pdf.ScolarsPageTemplate(
|
||||
sco_pdf.ScoDocPageTemplate(
|
||||
document,
|
||||
author="%s %s (E. Viennet) [%s]"
|
||||
% (sco_version.SCONAME, sco_version.SCOVERSION, self.description),
|
||||
|
@ -54,9 +54,7 @@ import io
|
||||
import re
|
||||
import time
|
||||
import traceback
|
||||
from pydoc import html
|
||||
|
||||
from reportlab.platypus.doctemplate import BaseDocTemplate
|
||||
import pydoc
|
||||
|
||||
from flask import g, request
|
||||
|
||||
@ -74,17 +72,17 @@ import app.scodoc.sco_utils as scu
|
||||
import sco_version
|
||||
|
||||
|
||||
def pdfassemblebulletins(
|
||||
formsemestre_id,
|
||||
objects,
|
||||
bul_title,
|
||||
def assemble_bulletins_pdf(
|
||||
formsemestre_id: int,
|
||||
story: list,
|
||||
bul_title: str,
|
||||
infos,
|
||||
pagesbookmarks,
|
||||
filigranne=None,
|
||||
server_name="",
|
||||
):
|
||||
"generate PDF document from a list of PLATYPUS objects"
|
||||
if not objects:
|
||||
"Generate PDF document from a story (list of PLATYPUS objects)."
|
||||
if not story:
|
||||
return ""
|
||||
# Paramètres de mise en page
|
||||
margins = (
|
||||
@ -93,11 +91,10 @@ def pdfassemblebulletins(
|
||||
sco_preferences.get_preference("right_margin", formsemestre_id),
|
||||
sco_preferences.get_preference("bottom_margin", formsemestre_id),
|
||||
)
|
||||
|
||||
report = io.BytesIO() # in-memory document, no disk file
|
||||
document = BaseDocTemplate(report)
|
||||
document = sco_pdf.BulletinDocTemplate(report)
|
||||
document.addPageTemplates(
|
||||
sco_pdf.ScolarsPageTemplate(
|
||||
sco_pdf.ScoDocPageTemplate(
|
||||
document,
|
||||
author="%s %s (E. Viennet)" % (sco_version.SCONAME, sco_version.SCOVERSION),
|
||||
title="Bulletin %s" % bul_title,
|
||||
@ -109,7 +106,8 @@ def pdfassemblebulletins(
|
||||
preferences=sco_preferences.SemPreferences(formsemestre_id),
|
||||
)
|
||||
)
|
||||
document.build(objects)
|
||||
document.build(story)
|
||||
# document.multiBuild(story)
|
||||
data = report.getvalue()
|
||||
return data
|
||||
|
||||
@ -121,7 +119,8 @@ def replacement_function(match):
|
||||
if logo is not None:
|
||||
return r'<img %s src="%s"%s/>' % (match.group(2), logo.filepath, match.group(4))
|
||||
raise ScoValueError(
|
||||
'balise "%s": logo "%s" introuvable' % (html.escape(balise), html.escape(name))
|
||||
'balise "%s": logo "%s" introuvable'
|
||||
% (pydoc.html.escape(balise), pydoc.html.escape(name))
|
||||
)
|
||||
|
||||
|
||||
@ -205,7 +204,7 @@ def get_formsemestre_bulletins_pdf(formsemestre_id, version="selectedevals"):
|
||||
server_name = ""
|
||||
try:
|
||||
sco_pdf.PDFLOCK.acquire()
|
||||
pdfdoc = pdfassemblebulletins(
|
||||
pdfdoc = assemble_bulletins_pdf(
|
||||
formsemestre_id,
|
||||
fragments,
|
||||
formsemestre.titre_mois(),
|
||||
@ -255,7 +254,7 @@ def get_etud_bulletins_pdf(etudid, version="selectedevals"):
|
||||
server_name = ""
|
||||
try:
|
||||
sco_pdf.PDFLOCK.acquire()
|
||||
pdfdoc = pdfassemblebulletins(
|
||||
pdfdoc = assemble_bulletins_pdf(
|
||||
None,
|
||||
fragments,
|
||||
etud["nomprenom"],
|
||||
|
@ -73,7 +73,7 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
description = "standard ScoDoc (version 2011)" # la description doit être courte: elle apparait dans le menu de paramètrage ScoDoc
|
||||
supported_formats = ["html", "pdf"]
|
||||
|
||||
def bul_title_pdf(self):
|
||||
def bul_title_pdf(self) -> list:
|
||||
"""Génère la partie "titre" du bulletin de notes.
|
||||
Renvoie une liste d'objets platypus
|
||||
"""
|
||||
@ -115,11 +115,11 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
- en PDF: une liste d'objets platypus
|
||||
"""
|
||||
H = [] # html
|
||||
Op = [] # objets platypus
|
||||
story = [] # objets platypus
|
||||
# ----- ABSENCES
|
||||
if self.preferences["bul_show_abs"]:
|
||||
nbabs = self.infos["nbabs"]
|
||||
Op.append(Spacer(1, 2 * mm))
|
||||
story.append(Spacer(1, 2 * mm))
|
||||
if nbabs:
|
||||
H.append(
|
||||
"""<p class="bul_abs">
|
||||
@ -130,7 +130,7 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
"""
|
||||
% self.infos
|
||||
)
|
||||
Op.append(
|
||||
story.append(
|
||||
Paragraph(
|
||||
SU(
|
||||
"%(nbabs)s absences (1/2 journées), dont %(nbabsjust)s justifiées."
|
||||
@ -141,7 +141,7 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
)
|
||||
else:
|
||||
H.append("""<p class="bul_abs">Pas d'absences signalées.</p>""")
|
||||
Op.append(Paragraph(SU("Pas d'absences signalées."), self.CellStyle))
|
||||
story.append(Paragraph(SU("Pas d'absences signalées."), self.CellStyle))
|
||||
|
||||
# ---- APPRECIATIONS
|
||||
# le dir. des etud peut ajouter des appreciations,
|
||||
@ -168,10 +168,10 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
% self.infos
|
||||
)
|
||||
H.append("</div>")
|
||||
# Appreciations sur PDF:
|
||||
# Appréciations sur PDF:
|
||||
if self.infos.get("appreciations_list", False):
|
||||
Op.append(Spacer(1, 3 * mm))
|
||||
Op.append(
|
||||
story.append(Spacer(1, 3 * mm))
|
||||
story.append(
|
||||
Paragraph(
|
||||
SU("Appréciation : " + "\n".join(self.infos["appreciations_txt"])),
|
||||
self.CellStyle,
|
||||
@ -180,7 +180,7 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
|
||||
# ----- DECISION JURY
|
||||
if self.preferences["bul_show_decision"]:
|
||||
Op += sco_bulletins_pdf.process_field(
|
||||
story += sco_bulletins_pdf.process_field(
|
||||
self.preferences["bul_pdf_caption"],
|
||||
self.infos,
|
||||
self.FieldStyle,
|
||||
@ -196,7 +196,12 @@ class BulletinGeneratorStandard(sco_bulletins_generator.BulletinGenerator):
|
||||
|
||||
# -----
|
||||
if format == "pdf":
|
||||
return [KeepTogether(Op)]
|
||||
if self.scale_table_in_page:
|
||||
# le scaling (pour tenir sur une page) semble incompatible avec
|
||||
# le KeepTogether()
|
||||
return story
|
||||
else:
|
||||
return [KeepTogether(story)]
|
||||
elif format == "html":
|
||||
return "\n".join(H)
|
||||
|
||||
|
@ -175,7 +175,27 @@ def bold_paras(L, tag="b", close=None):
|
||||
return [b + (x or "") + close for x in L]
|
||||
|
||||
|
||||
class ScolarsPageTemplate(PageTemplate):
|
||||
class BulMarker(Flowable):
|
||||
"""Custom Flowables pour nos bulletins PDF: invisibles, juste pour se repérer"""
|
||||
|
||||
def wrap(self, *args):
|
||||
return (0, 0)
|
||||
|
||||
def draw(self):
|
||||
return
|
||||
|
||||
|
||||
class DebutBulletin(BulMarker):
|
||||
"""Début d'un bulletin.
|
||||
Element vide utilisé pour générer les bookmarks
|
||||
"""
|
||||
|
||||
def __init__(self, bookmark=None):
|
||||
self.bookmark = bookmark
|
||||
super().__init__()
|
||||
|
||||
|
||||
class ScoDocPageTemplate(PageTemplate):
|
||||
"""Our own page template."""
|
||||
|
||||
def __init__(
|
||||
@ -203,6 +223,8 @@ class ScolarsPageTemplate(PageTemplate):
|
||||
self.pdfmeta_subject = subject
|
||||
self.server_name = server_name
|
||||
self.filigranne = filigranne
|
||||
self.page_number = 1
|
||||
self.current_page_bookmark = None
|
||||
self.footer_template = footer_template
|
||||
if self.preferences:
|
||||
self.with_page_background = self.preferences["bul_pdf_with_background"]
|
||||
@ -217,7 +239,7 @@ class ScolarsPageTemplate(PageTemplate):
|
||||
document.pagesize[0] - 20.0 * mm - left * mm - right * mm,
|
||||
document.pagesize[1] - 18.0 * mm - top * mm - bottom * mm,
|
||||
)
|
||||
PageTemplate.__init__(self, "ScolarsPageTemplate", [content])
|
||||
super().__init__("ScoDocPageTemplate", [content])
|
||||
self.logo = None
|
||||
logo = find_logo(
|
||||
logoname="bul_pdf_background", dept_id=g.scodoc_dept_id
|
||||
@ -265,21 +287,6 @@ class ScolarsPageTemplate(PageTemplate):
|
||||
) = self.logo
|
||||
canvas.drawImage(image, inch, doc.pagesize[1] - inch, width, height)
|
||||
|
||||
# ---- Filigranne (texte en diagonal en haut a gauche de chaque page)
|
||||
if self.filigranne:
|
||||
if isinstance(self.filigranne, str):
|
||||
filigranne = self.filigranne # same for all pages
|
||||
else:
|
||||
filigranne = self.filigranne.get(doc.page, None)
|
||||
if filigranne:
|
||||
canvas.saveState()
|
||||
canvas.translate(9 * cm, 27.6 * cm)
|
||||
canvas.rotate(30)
|
||||
canvas.scale(4.5, 4.5)
|
||||
canvas.setFillColorRGB(1.0, 0.65, 0.65)
|
||||
canvas.drawRightString(0, 0, SU(filigranne))
|
||||
canvas.restoreState()
|
||||
|
||||
# ---- Add some meta data and bookmarks
|
||||
if self.pdfmeta_author:
|
||||
canvas.setAuthor(SU(self.pdfmeta_author))
|
||||
@ -287,12 +294,16 @@ class ScolarsPageTemplate(PageTemplate):
|
||||
canvas.setTitle(SU(self.pdfmeta_title))
|
||||
if self.pdfmeta_subject:
|
||||
canvas.setSubject(SU(self.pdfmeta_subject))
|
||||
bm = self.pagesbookmarks.get(doc.page, None)
|
||||
if bm != None:
|
||||
key = bm
|
||||
txt = SU(bm)
|
||||
canvas.bookmarkPage(key)
|
||||
canvas.addOutlineEntry(txt, bm)
|
||||
# if self.current_page_bookmark:
|
||||
# canvas.bookmarkPage(self.current_page_bookmark)
|
||||
# canvas.addOutlineEntry(
|
||||
# SU(self.current_page_bookmark), self.current_page_bookmark
|
||||
# )
|
||||
# else: XXX A REMETTRE
|
||||
# bookmark = self.pagesbookmarks.get(doc.page, None)
|
||||
# if bookmark != None:
|
||||
# canvas.bookmarkPage(bookmark)
|
||||
# canvas.addOutlineEntry(SU(bookmark), bookmark)
|
||||
# ---- Footer
|
||||
canvas.setFont(
|
||||
self.preferences["SCOLAR_FONT"], self.preferences["SCOLAR_FONT_SIZE_FOOT"]
|
||||
@ -308,6 +319,48 @@ class ScolarsPageTemplate(PageTemplate):
|
||||
)
|
||||
canvas.restoreState()
|
||||
|
||||
def afterDrawPage(self, canvas, doc):
|
||||
if not self.preferences:
|
||||
return
|
||||
# ---- Filigranne (texte en diagonal en haut a gauche de chaque page)
|
||||
if self.filigranne:
|
||||
if isinstance(self.filigranne, str):
|
||||
filigranne = self.filigranne # same for all pages
|
||||
else:
|
||||
filigranne = self.filigranne.get(doc.page, None)
|
||||
if filigranne:
|
||||
canvas.saveState()
|
||||
canvas.translate(9 * cm, 27.6 * cm)
|
||||
canvas.rotate(30)
|
||||
canvas.scale(4.5, 4.5)
|
||||
canvas.setFillColorRGB(1.0, 0.65, 0.65, alpha=0.6)
|
||||
canvas.drawRightString(0, 0, SU(filigranne))
|
||||
canvas.restoreState()
|
||||
|
||||
def afterPage(self):
|
||||
"""Called after all flowables have been drawn on a page.
|
||||
Increment pageNum since the page has been completed.
|
||||
"""
|
||||
self.page_number += 1
|
||||
self.current_page_bookmark = None
|
||||
|
||||
|
||||
class BulletinDocTemplate(BaseDocTemplate):
|
||||
"""Doc template pour les bulletins PDF
|
||||
ajoute la gestion des bookmarks
|
||||
"""
|
||||
|
||||
# inspired by https://www.reportlab.com/snippets/13/
|
||||
def afterFlowable(self, flowable):
|
||||
"""Called by Reportlab after each flowable"""
|
||||
if isinstance(flowable, DebutBulletin):
|
||||
if flowable.bookmark:
|
||||
self.canv.bookmarkPage(flowable.bookmark)
|
||||
self.canv.addOutlineEntry(
|
||||
SU(flowable.bookmark), flowable.bookmark, level=0, closed=None
|
||||
)
|
||||
# log(f"afterFlowable addOutlineEntry {flowable.bookmark} page {self.page}")
|
||||
|
||||
|
||||
def _makeTimeDict():
|
||||
# ... suboptimal but we don't care
|
||||
@ -333,7 +386,7 @@ def pdf_basic_page(
|
||||
report = io.BytesIO() # in-memory document, no disk file
|
||||
document = BaseDocTemplate(report)
|
||||
document.addPageTemplates(
|
||||
ScolarsPageTemplate(
|
||||
ScoDocPageTemplate(
|
||||
document,
|
||||
title=title,
|
||||
author="%s %s (E. Viennet)" % (sco_version.SCONAME, sco_version.SCOVERSION),
|
||||
|
@ -378,7 +378,7 @@ def _trombino_pdf(groups_infos):
|
||||
# Build document
|
||||
document = BaseDocTemplate(report)
|
||||
document.addPageTemplates(
|
||||
sco_pdf.ScolarsPageTemplate(
|
||||
sco_pdf.ScoDocPageTemplate(
|
||||
document,
|
||||
preferences=sco_preferences.SemPreferences(sem["formsemestre_id"]),
|
||||
)
|
||||
@ -458,7 +458,7 @@ def _listeappel_photos_pdf(groups_infos):
|
||||
# Build document
|
||||
document = BaseDocTemplate(report)
|
||||
document.addPageTemplates(
|
||||
sco_pdf.ScolarsPageTemplate(
|
||||
sco_pdf.ScoDocPageTemplate(
|
||||
document,
|
||||
preferences=sco_preferences.SemPreferences(sem["formsemestre_id"]),
|
||||
)
|
||||
|
@ -264,7 +264,7 @@ def pdf_trombino_tours(
|
||||
filename = "trombino-%s-%s.pdf" % (DeptName, groups_infos.groups_filename)
|
||||
document = BaseDocTemplate(report)
|
||||
document.addPageTemplates(
|
||||
ScolarsPageTemplate(
|
||||
ScoDocPageTemplate(
|
||||
document,
|
||||
preferences=sco_preferences.SemPreferences(),
|
||||
)
|
||||
@ -460,7 +460,7 @@ def pdf_feuille_releve_absences(
|
||||
else:
|
||||
document = BaseDocTemplate(report, pagesize=taille)
|
||||
document.addPageTemplates(
|
||||
ScolarsPageTemplate(
|
||||
ScoDocPageTemplate(
|
||||
document,
|
||||
preferences=sco_preferences.SemPreferences(),
|
||||
)
|
||||
|
Loading…
Reference in New Issue
Block a user