ScoDoc/app/but/apc_edit_ue.py

126 lines
4.6 KiB
Python

##############################################################################
# ScoDoc
# Copyright (c) 1999 - 2024 Emmanuel Viennet. All rights reserved.
# See LICENSE
##############################################################################
"""
Edition associations UE <-> Ref. Compétence
"""
from flask import g, url_for
from app.models import ApcReferentielCompetences, UniteEns
from app.scodoc import codes_cursus
def form_ue_choix_parcours(ue: UniteEns) -> str:
"""Form. HTML pour associer une UE à ses parcours.
Le menu select lui même est vide et rempli en JS par appel à get_ue_niveaux_options_html
"""
if ue.type != codes_cursus.UE_STANDARD:
return ""
ref_comp = ue.formation.referentiel_competence
if ref_comp is None:
return f"""<div class="ue_advanced">
<div class="warning">Pas de référentiel de compétence associé à cette formation !</div>
<div><a class="stdlink" href="{ url_for('notes.refcomp_assoc_formation',
scodoc_dept=g.scodoc_dept, formation_id=ue.formation.id)
}">associer un référentiel de compétence</a>
</div>
</div>"""
H = [
"""
<div class="ue_advanced">
<h3>Parcours du BUT</h3>
"""
]
# Choix des parcours
ue_pids = [p.id for p in ue.parcours]
H.append("""<form id="choix_parcours">""")
ects_differents = {
ue.get_ects(parcour, only_parcours=True) for parcour in ref_comp.parcours
} != {None}
for parcour in ref_comp.parcours:
ects_parcour = ue.get_ects(parcour)
ects_parcour_txt = (
f" ({ue.get_ects(parcour):.3g} ects)" if ects_differents else ""
)
H.append(
f"""<label><input type="checkbox" name="{parcour.id}" value="{parcour.id}"
{'checked' if parcour.id in ue_pids else ""}
onclick="set_ue_parcour(this);"
data-setter="{url_for("apiweb.set_ue_parcours",
scodoc_dept=g.scodoc_dept, ue_id=ue.id)}"
>{parcour.code}{ects_parcour_txt}</label>"""
)
H.append("""</form>""")
#
H.append(
f"""
<ul>
<li>
<a class="stdlink" href="{
url_for("notes.ue_parcours_ects",
scodoc_dept=g.scodoc_dept, ue_id=ue.id)
}">définir des ECTS différents dans chaque parcours</a>
</li>
</ul>
</div>
"""
)
return "\n".join(H)
def get_ue_niveaux_options_html(ue: UniteEns) -> str:
"""fragment html avec les options du menu de sélection du
niveau de compétences associé à une UE.
Si l'UE n'a pas de parcours associé: présente les niveaux
de tous les parcours.
Si l'UE a un parcours: seulement les niveaux de ce parcours.
"""
ref_comp: ApcReferentielCompetences = ue.formation.referentiel_competence
if ref_comp is None:
return ""
# Les niveaux:
annee = ue.annee() # 1, 2, 3
parcours, niveaux_by_parcours = ref_comp.get_niveaux_by_parcours(annee, ue.parcours)
# Les niveaux déjà associés à d'autres UE du même semestre
autres_ues = ue.formation.ues.filter_by(semestre_idx=ue.semestre_idx)
niveaux_autres_ues = {
oue.niveau_competence_id for oue in autres_ues if oue.id != ue.id
}
options = []
if niveaux_by_parcours["TC"]: # TC pour Tronc Commun
options.append("""<optgroup label="Tronc commun">""")
for n in niveaux_by_parcours["TC"]:
options.append(
f"""<option value="{n.id}" {
'selected' if ue.niveau_competence == n else ''}
>{n.annee} {n.competence.titre} / {n.competence.titre_long}
niveau {n.ordre}</option>"""
)
options.append("""</optgroup>""")
for parcour in parcours:
if len(niveaux_by_parcours[parcour.id]):
options.append(f"""<optgroup label="Parcours {parcour.libelle}">""")
for n in niveaux_by_parcours[parcour.id]:
if n.id in niveaux_autres_ues:
disabled = "disabled"
else:
disabled = ""
options.append(
f"""<option value="{n.id}" {'selected'
if ue.niveau_competence == n else ''}
{disabled}>{n.annee} {n.competence.titre} / {n.competence.titre_long}
niveau {n.ordre}</option>"""
)
options.append("""</optgroup>""")
return (
f"""<option value="" {'selected' if ue.niveau_competence is None else ''}>aucun</option>"""
+ "\n".join(options)
)