Leonel FOFOU
2026-07-28 32450e295200b2bc7896518ff74161ff26772e2d
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
package com.megatim.manuel.core.convert;
 
import java.text.Normalizer;
 
/**
 * Reconnaît les « pages liminaires » standard d'un document (résumé, mots clés,
 * historique des versions, diffusion, table des illustrations, sommaire) d'après leur intitulé,
 * indépendamment du style. Sert à structurer la navigation de l'aide.
 */
public final class FrontMatter {
 
    public static final String RESUME = "RESUME";
    public static final String MOTSCLES = "MOTSCLES";
    public static final String HISTORIQUE = "HISTORIQUE";
    public static final String DIFFUSION = "DIFFUSION";
    public static final String TABLEILLUS = "TABLEILLUS";
    public static final String SOMMAIRE = "SOMMAIRE";
 
    /** Entrées affichées comme repères de navigation, dans l'ordre canonique. */
    public static final String[] ENTRY_ORDER = { RESUME, MOTSCLES, HISTORIQUE, DIFFUSION };
 
    private FrontMatter() {}
 
    /** Renvoie la clé de section liminaire correspondant au texte, ou null. */
    public static String match(String text) {
        if (text == null) return null;
        String n = deaccent(text.trim().toLowerCase());
        if (n.isEmpty() || n.length() > 80) return null; // un intitulé est court
        // ordre important : "table des illustrations" avant "sommaire/table des matières"
        if (n.startsWith("table des illustration") || n.startsWith("table des figure")
                || n.startsWith("liste des illustration") || n.startsWith("liste des figure")) return TABLEILLUS;
        if (n.startsWith("resume")) return RESUME;
        if (n.startsWith("mots cle") || n.startsWith("mot cle") || n.startsWith("mots-cle") || n.startsWith("mot-cle")) return MOTSCLES;
        if (n.startsWith("historique")) return HISTORIQUE;
        if (n.startsWith("diffusion") || n.startsWith("liste de diffusion")) return DIFFUSION;
        if (n.startsWith("sommaire") || n.startsWith("table des matiere")) return SOMMAIRE;
        return null;
    }
 
    /** Vrai si la clé doit apparaître comme repère cliquable (les autres sont structurelles). */
    public static boolean isEntry(String key) {
        for (String k : ENTRY_ORDER) if (k.equals(key)) return true;
        return false;
    }
 
    /** Libellé court affiché pour une clé d'entrée (regroupée sous « Préambule »). */
    public static String label(String key) {
        switch (key) {
            case RESUME:     return "Résumé";
            case MOTSCLES:   return "Mots clés";
            case HISTORIQUE: return "Historique";
            case DIFFUSION:  return "Diffusion";
            default:         return key;
        }
    }
 
    private static String deaccent(String s) {
        return Normalizer.normalize(s, Normalizer.Form.NFD).replaceAll("\\p{M}+", "");
    }
}