imported>Jacques Ducloy |
imported>Jacques Ducloy |
Ligne 1 : |
Ligne 1 : |
− | local fun = {}
| + | <includeonly><no</includeonly><includeonly>include>{{documentation modèle vue directement}}</no</includeonly><includeonly>include> |
| | | |
− | local TableBuilder = require( 'Module:TableBuilder' )
| + | ==Utilisation== |
− | local Outils = require( 'Module:Outils' )
| + | : Description du rôle de ce modèle à compléter. |
− | -- chargement de la base de donnée répertoriant certaines pages existant ou n'existant pas pour éviter les "ifexist".
| |
− | local dataLiens
| |
− | local success, resultat = pcall ( mw.loadData, 'Module:Date/Data' )
| |
− | if success then
| |
− | dataLiens = resultat
| |
− | else
| |
− | -- protection au cas ou le sous module serait mal modifié
| |
− | dataLiens = { [''] = { mois = { aucun = 1000, tous = { 1773, 2014 } }, } }
| |
− | end
| |
| | | |
− | -- nettoie un paramètre non nommé (vire les espaces au début et à la fin)
| + | ==Syntaxe== |
− | -- retourne nil si le texte est vide ou n'est pas du texte. Attention c'est important pour les fonction qui l'utilise.
| + | * <code><nowiki>{{</nowiki>{{sub</includeonly><includeonly>st:BASEPAGENAME}}<nowiki>|paramètre1|nom1param=valeur1}}</nowiki></code> |
− | local trim = Outils.trim
| |
| | | |
− | -- Fonction destiné à mettre la première lettre du mois en majuscule du mois :
| + | ==Paramètres== |
− | -- utilisation de string car aucun mois ne commance par une lettre non ascii en français ou anglais.
| + | * '''1''' = ''paramètre1'' – description (obligatoire/optionnel, par défaut ''valeur'') |
− | local function ucfirst( str )
| + | * '''nom1param''' = ''valeur1'' – description (obligatoire/optionnel, par défaut ''valeur'') |
− | return str:sub( 1, 1 ):upper() .. str:sub( 2 )
| |
− | end
| |
| | | |
− | local modelePremier = '<abbr class="abbr" title="premier">1<sup>er</sup></abbr>'
| + | ==Exemple== |
| + | * <code><nowiki>{{</nowiki>{{sub</includeonly><includeonly>st:BASEPAGENAME}}<nowiki>|paramètre1|nom1param=valeur1}}</nowiki></code> |
| + | {{{{sub</includeonly><includeonly>st:BASEPAGENAME}}|paramètre1|nom1param=valeur1}} |
| | | |
| + | <include</includeonly><includeonly>only> |
| + | <!-- Catégories pour le [[Modèle:{{sub</includeonly><includeonly>st:BASEPAGENAME}}]]--> |
| + | {{DEFAULTSORT:{{sub</includeonly><includeonly>st:BASEPAGENAME}}}}<!-- à remplacer si le nom du modèle a des accents --> |
| + | [[Catégorie:Espace Modèle<!-- RECHERCHEZ UNE SOUS-CATEGORIE APPROPRIÉE -->]] |
| | | |
− | -- liste des mois, écriture exacte et simplifiée, en minuscule | + | <!-- Interwikis pour le [[Modèle:{{sub</includeonly><includeonly>st:BASEPAGENAME}}]]--> |
− | local liste_mois = {
| + | [[en:Template:{{sub</includeonly><includeonly>st:BASEPAGENAME}}]] |
− | { "janvier", "jan.", "janv.", "jan", "janv", "january", nJour = 31 },
| |
− | { "février", "fevrier", "fev.", "fev", "fév.", "fév", "févr", "févr.", "february", nJour = 29 },
| |
− | { "mars", "mar.", "mar", "march", nJour = 31 },
| |
− | { "avril", "avr.", "avr", "apr", "april", nJour = 30 },
| |
− | { "mai", "may", nJour = 31 },
| |
− | { "juin", "jun", "june", nJour = 30 },
| |
− | { "juillet", "juil.", "juil", "juill.", "juill", "jul", "july", nJour = 31 },
| |
− | { "août", "aout", "aou", "aug", "august", nJour = 31 },
| |
− | { "septembre", "sept.", "sept", "sep.", "sep", "september", nJour = 30 },
| |
− | { "octobre", "oct.", "oct", "october", nJour = 31 },
| |
− | { "novembre", "nov.", "nov", "november", nJour = 30 },
| |
− | { "décembre", "decembre", "déc.", "dec.", "dec", "déc", "december", nJour = 31 },
| |
− | } | |
− | fun.liste_mois = liste_mois
| |
| | | |
− | local liste_saison = {
| + | </include</includeonly><includeonly>only></includeonly> |
− | { 'printemps', 'spring', },
| |
− | { 'été', 'summer', },
| |
− | { 'automne', 'autumn', },
| |
− | { 'hiver', 'winter', },
| |
− | }
| |
− | | |
− | -- nom du mois à partir du numéro
| |
− | function fun.nomDuMois( num )
| |
− | if type( num ) ~= "number" or num < 1 or num > 12 then
| |
− | return nil
| |
− | end
| |
− | return liste_mois[num][1]
| |
− | end
| |
− | | |
− | ---
| |
− | -- valide que la chaîne passée est un mois valide.
| |
− | -- retourne le nom complet ou nil si non reconnu
| |
− | -- si reconnu, retourne aussi le numéro du mois [1-12]
| |
− | function fun.valideMois( mois )
| |
− | local m = trim( mois )
| |
− | if m then
| |
− | m = mw.ustring.lower( m )
| |
− | for i = 1, 12 do
| |
− | local j = 1
| |
− | while liste_mois[i][j] do
| |
− | if liste_mois[i][j] == m then
| |
− | return liste_mois[i][1], i
| |
− | end
| |
− | j = j + 1
| |
− | end
| |
− | end
| |
− | end
| |
− | -- pas trouvé = return nil
| |
− | end
| |
− | | |
− | ---
| |
− | -- valide que la chaîne passée est un mois valide.
| |
− | -- retourne le nom complet ou nil si non reconnu
| |
− | -- si reconnu, retourne aussi le numéro du mois [1-12]
| |
− | function fun.valideSaison( saison )
| |
− | if type( saison ) ~= "string" then
| |
− | return nil
| |
− | end
| |
− |
| |
− | local m = mw.ustring.lower( trim( saison ) )
| |
− |
| |
− | for i = 1, 4 do
| |
− | local j = 1
| |
− | while liste_saison[i][j] ~= nil do
| |
− | if liste_saison[i][j] == m then
| |
− | return liste_saison[i][1]
| |
− | end
| |
− | j = j + 1
| |
− | end
| |
− | end
| |
− | -- pas trouvé = return nil
| |
− | end
| |
− | | |
− | ---
| |
− | -- determinationMois trouve le numéro du mois et son nom,
| |
− | -- à partir de son nom, de son numéro ou d'une expression mathématique.
| |
− | -- Si le deuxième paramètre est vrai, les nombres supérieur à 12 ou non entiers sont acceptés.
| |
− | function fun.determinationMois( mois, mod, boucle )
| |
− | local num, nom
| |
− | if tonumber( mois ) then
| |
− | num = math.floor( tonumber( mois ) )
| |
− | if mod then
| |
− | -- si le nombre du mois est calculé par une exression, le résultat peut être supérieur à 12, ou inférieur à 1
| |
− | num = math.fmod( num + 239, 12 ) + 1 -- +239 car fmod(-1) = -1 et non 11
| |
− | elseif num < 1 or num > 12 then
| |
− | num = nil
| |
− | end
| |
− | elseif trim( mois ) then
| |
− | nom, num = fun.valideMois( mois )
| |
− | if nom == nil and boucle == nil then
| |
− | -- essai de détermination d'un nombre avec le parser #expr de Mediawiki.
| |
− | -- le paramètre boucle évite de tourner en boucle.
| |
− | nom, num = fun.determinationMois( mw.getCurrentFrame():callParserFunction( '#expr', mois ), true, true )
| |
− | end
| |
− | end
| |
− | if num and not nom then
| |
− | nom = liste_mois[num][1]
| |
− | end
| |
− | return nom, num
| |
− | end
| |
− | | |
− | | |
− | -- fonction interne à modeleDate, pour déterminer si on peut se passer de faire un ifexit
| |
− | local function existDate( dataQualificatif, annee, mois )
| |
− | local data
| |
− | if mois then
| |
− | data = dataQualificatif.mois
| |
− | else
| |
− | data = dataQualificatif.annee
| |
− | end
| |
− | if type( data ) ~= 'table' then
| |
− | -- si data n'existe pas c'est que l'on considère qu'il n'y a pas de lien.
| |
− | return
| |
− | end
| |
− | -- le qualificatif est remplacer par celui de la base de donnée, ce qui permet des alias.
| |
− | local lien = annee .. ' ' .. ( dataQualificatif.qualificatif or '' )
| |
− | local seul = annee
| |
− | if mois then
| |
− | lien = mois .. ' ' .. lien
| |
− | seul = ucfirst( mois ) .. ' ' .. annee
| |
− | end
| |
− | local aucun = tonumber( data.aucun )
| |
− | if aucun and annee <= aucun then
| |
− | -- si la l'année est dans la partie 'aucun' on teste s'il y a malgré tout un lien isolé
| |
− | if type( data.seul ) == 'table' then
| |
− | for i, v in ipairs( data.seul ) do
| |
− | if seul == v or seul == tonumber( v ) then
| |
− | return lien
| |
− | end
| |
− | end
| |
− | end
| |
− | -- partie aucun et pas de lien => nil
| |
− | return nil
| |
− | elseif type( data.tous ) == 'table' then
| |
− | local tous1, tous2 = tonumber( data.tous[1] ), tonumber( data.tous[2] )
| |
− | if tous1 and tous2 and annee >= tous1 and annee <= tous2 then
| |
− | -- l'année est dans la partie 'tous' donc on retourne le lien
| |
− | return lien
| |
− | end
| |
− | end
| |
− | -- l'annee n'est ni dans la partie aucun, ni dans la partie tous donc il faut tester si la page existe.
| |
− | local cibleLien = mw.title.new( lien )
| |
− | if cibleLien and cibleLien.exists then
| |
− | return lien
| |
− | end
| |
− | end
| |
− | | |
− | ---
| |
− | -- Supprime le jour de la semaine, et "le" avant une date
| |
− | function fun.nettoyageJour( jour )
| |
− | if type( jour ) == 'string' then
| |
− | local nomJour = { '[Ll]undi', '[Mm]ardi', '[Mm]ercredi', '[Jj]eudi', '[Vv]endredi',
| |
− | '[Ss]amedi', '[Dd]imanche', '^ *[Ll]e' }
| |
− | local premier = { '<abbr class="abbr" title="Premier" >1<sup>er</sup></abbr>', '1<sup>er</sup>', '1er' }
| |
− | for i, v in ipairs( nomJour ) do
| |
− | jour = jour:gsub( v, '' )
| |
− | end
| |
− | for i, v in ipairs( premier ) do
| |
− | jour = jour:gsub( v, '1' )
| |
− | end
| |
− | jour = trim( jour )
| |
− | end
| |
− | return jour
| |
− | end
| |
− | | |
− | ---
| |
− | -- Sépare une chaine date en un table contenant les champs jour, mois et annee.
| |
− | -- la date doit contenir le mois.
| |
− | function fun.separationJourMoisAnnee( date )
| |
− | date = trim( date )
| |
− | if date then
| |
− | local function erreur( periode, valeur )
| |
− | return false, Outils.erreur( periode .. ' invalide (' .. valeur .. ')' )
| |
− | end
| |
− | local jour, mois, annee, masquerMois, masquerAnnee, separateur
| |
− | -- variable pour construire les regex
| |
− | local j = '([0-3]?%d)' -- jour
| |
− | local m = '([01]?%d)' -- mois numérique
| |
− | local mmm = '([^%s%p%d]+[.]?)' -- mois en toute lettre
| |
− | local aj = '(%-?%d+)' -- année ou jour
| |
− | local s = '[ ./-]+' -- séparateur simple
| |
− | local sep = '([ ./-]+)' -- séparateur avec capture, pour le détecter deux fois
| |
− | local moins = '(%-?)' -- signe moins pour signifier qu'il ne faut pas afficher cette donnée
| |
− | local regexb = {
| |
− | jmmm = '^'..j..s..mmm..moins..'$',
| |
− | mmmjva = '^'..mmm..s..j..', ?'..aj..'$',
| |
− | }
| |
− |
| |
− | date = fun.nettoyageJour( date )
| |
− | -- suppression catégorie, liens, balises
| |
− | date = mw.ustring.gsub( date, '%[%[[Cc]at[ée]gor[yi]e?:.-%]%]', '' )
| |
− | date = date :gsub( '%b<>', '' )
| |
− | :gsub( '%[%[([^%[%]|]*)|?([^%[%]]*)%]%]', function ( l, t ) return trim( t ) or l end )
| |
− | -- suppression des espaces insécables
| |
− | :gsub( '\194\160', ' ' )
| |
− | :gsub( ' ', ' ' )
| |
− | :gsub( '\226\128\175', ' ' )
| |
− | :gsub( '&nnbsp;', ' ' )
| |
− | :gsub( '\226\128\137', ' ' )
| |
− | :gsub( ' ', ' ' )
| |
− | :gsub( ' ', ' ' )
| |
− | :gsub( ' +', ' ' )
| |
− | -- réduction av. J-C pour simplifier un peu les regex :
| |
− | :gsub( '(%d+) ?[Aa][Vv]%.? ?[Jj][ .-]*[Cc]%.?', '-%1' )
| |
− | -- supression de l'heure dans les date ISO
| |
− | :gsub( '^+?([%d-]*%d%d%-%d%d)T%d%d[%d:,.+-]*Z?$' , '%1')
| |
− |
| |
− | -- test année seule
| |
− | if date:match( '^'..aj..'$' ) then
| |
− | annee = date:match( '^'..aj..'$' )
| |
− | elseif date:match( '^'..aj..s..aj..moins..'$' ) then
| |
− | -- jj/mm, mm/aaaa ou aaaa/mm
| |
− | local a, separateur, b, sb = date:match( '^'..aj..sep..aj..moins..'$' )
| |
− | a, b = tonumber( a ), tonumber( b )
| |
− | if separateur:match( '^.+%-$' ) then
| |
− | -- probablement mm/-aaaa, année av.JC
| |
− | b = 0 - b
| |
− | end
| |
− | if a > 12 and ( b < 1 or b > 31 ) or
| |
− | b > 12 and ( a < 1 or a > 31 ) then
| |
− | return erreur( 'Date', date )
| |
− | elseif b < 1 or b > 31 then
| |
− | mois, annee, masquerAnnee = a, b, sb
| |
− | elseif a < 1 or a > 31 then
| |
− | annee, mois = a, b
| |
− | elseif b > 12 then
| |
− | return erreur( 'Mois', b )
| |
− | else
| |
− | jour, mois, masquerMois = a, b, sb
| |
− | end
| |
− | elseif date:match( '^'..aj..sep..m..moins..'%2'..aj..moins..'$' ) then
| |
− | -- jj/mm/aaaa ou aaaa/mm/jj
| |
− | jour, separateur, mois, masquerMois, annee, masquerAnnee = date:match( '^'..aj..sep..m..moins..'%2'..aj..moins..'$' )
| |
− | if separateur == '-' and masquerMois == '-' and masquerAnnee == '' and tonumber( annee ) > 0 then
| |
− | -- date au format jj-mm--aaaa type 17-06--44 pour 17 juin 44 av. JC
| |
− | masquerMois = nil
| |
− | annee = 0 - annee
| |
− | end
| |
− | elseif date:match( '^'..j..sep..mmm..moins..'%2'..aj..moins..'$' ) then
| |
− | -- jj mmm aaaa
| |
− | jour, separateur, mois, masquerMois, annee, masquerAnnee = date:match( '^'..j..sep..mmm..moins..'%2'..aj..moins..'$' )
| |
− | elseif date:match( '^'..mmm..s..aj..moins..'$' ) then
| |
− | -- mmm aaaa
| |
− | mois, separateur, annee, masquerAnnee = date:match( '^'..mmm..sep..aj..moins..'$' )
| |
− | if separateur:match( '^.+%-$' ) then
| |
− | annee = '-' .. annee
| |
− | end
| |
− | elseif date:match( '^'..j..s..mmm..moins..'$' ) then
| |
− | -- jj mmmm
| |
− | jour, mois, masquerMois = date:match( '^'..j..s..mmm..moins..'$' )
| |
− | elseif date:match( '^'..mmm..s..j..', ?'..aj..'$') then
| |
− | -- mmm jj, aaaa (format anglo-saxon)
| |
− | mois, jour, annee = date:match( '^'..mmm..s..j..', ?'..aj..'$')
| |
− | elseif date:match( '^'..mmm..'$' ) then
| |
− | mois = date
| |
− | else
| |
− | return erreur( 'Date', date )
| |
− | end
| |
− | local jn, an = tonumber( jour ), tonumber( annee )
| |
− | if jn and an and ( jn > 31 or jn < 0 or #jour >= 3 ) and an <= 31 then
| |
− | -- cas notamment des date ISO 2015-06-17, -0044-06-17 et -0002-06-17
| |
− | -- inversion du jour et de l'année
| |
− | local temp = annee
| |
− | annee = jour
| |
− | jour = temp
| |
− | end
| |
− |
| |
− | return fun.validationJourMoisAnnee{
| |
− | jour, mois, annee,
| |
− | masquerAnnee = trim( masquerAnnee ) and true or nil,
| |
− | masquerMois = ( trim( masquerAnnee ) or not annee ) and trim( masquerMois ) and true or nil,
| |
− | -- or nil sert juste à éviter de trainer une valeur false dans tous les tests unitaires.
| |
− | }
| |
− | else
| |
− | return true, {}
| |
− | end
| |
− | end
| |
− | | |
− | | |
− | ---
| |
− | -- separationJourMoisAnnee prend jusqu'a cinq paramètre et essaie de les séparer en jour, mois, annee et qualificatif
| |
− | -- la date peut être dans le premier paramètre ou séparée dans les paramètre 1 à 3 ou 2 à 4.
| |
− | -- Le qualificatif est cherché dans le paramètre suivant.
| |
− | -- La fonction retourne true suivit d'une table avec la date en paramètres nommé (sans accent sur année)
| |
− | -- ou false suivit d'un message d'erreur.
| |
− | function fun.validationJourMoisAnnee( frame, ... )
| |
− | local args = Outils.extractArgs( frame, ... )
| |
− | local jour, mois, numMois, annee, erreur
| |
− | local bjour = args[1] or args['jour'] or ''
| |
− | local bmois = tostring( args[2] or args['mois'] or '' )
| |
− | local bannee = args[3] or args['annee'] or args['année'] or ''
| |
− |
| |
− | local function erreur( periode, valeur )
| |
− | return false, Outils.erreur( periode .. ' invalide (' .. valeur .. ')' )
| |
− | end
| |
− |
| |
− | -- on traite l'année
| |
− | if Outils.notEmpty( bannee ) then
| |
− | annee = tonumber( bannee )
| |
− | if annee == nil and type( bannee ) == 'string' then
| |
− | -- test si l'année contient av. J.-C.
| |
− | annee = string.match( string.upper( bannee ), '^(%d+) ?[Aa][Vv]%.? ?[Jj][ .-]*[Cc]%.?' )
| |
− | annee = tonumber( annee )
| |
− | if annee then
| |
− | annee = 0 - annee
| |
− | else
| |
− | return erreur( 'Année', bannee )
| |
− | end
| |
− | end
| |
− | else
| |
− | annee = nil
| |
− | end
| |
− |
| |
− | -- on traite le mois
| |
− | if Outils.notEmpty( bmois ) then
| |
− | mois, numMois = fun.determinationMois( bmois )
| |
− | if mois == nil then
| |
− | mois = fun.valideSaison( bmois )
| |
− | if mois == nil then
| |
− | return erreur( 'Mois', bmois )
| |
− | end
| |
− | else
| |
− | -- on traite le jour si présent
| |
− | if Outils.notEmpty( bjour ) then
| |
− | jour = tonumber( bjour )
| |
− | if jour == nil then
| |
− | jour = tonumber( fun.nettoyageJour( bjour ) )
| |
− | end
| |
− | if jour == nil then
| |
− | return erreur( 'Jour', bjour )
| |
− | end
| |
− | -- on valide que le jour est correct
| |
− | if jour < 1 or jour > 31 then
| |
− | return erreur( 'Jour', bjour )
| |
− | elseif jour > liste_mois[numMois].nJour then
| |
− | return erreur( 'Jour', bjour .. ' ' .. mois )
| |
− | elseif jour == 29 and numMois == 2 and annee and ( math.fmod( annee, 4 ) ~= 0 ) then
| |
− | -- l'année bisextile sur les siècles est toujours acceptée pour être compatible avec les dates juliennes.
| |
− | return erreur( 'Jour', '29 février ' .. annee )
| |
− | end
| |
− | else
| |
− | -- S'il n'y a pas de jour on regarde si la première lettre du mois est en majuscule
| |
− | if bmois:match( '^%u' ) then
| |
− | -- oui, on passe la première lettre en majuscule
| |
− | mois = ucfirst( mois )
| |
− | end
| |
− | -- s'il n'y a pas d'année non plus on retourne le mois simple
| |
− | end
| |
− | end
| |
− | else
| |
− | -- on teste le jour si présent
| |
− | if Outils.notEmpty( bjour ) then
| |
− | if annee then
| |
− | return erreur( 'Mois', 'absent' )
| |
− | else
| |
− | bjour = fun.nettoyageJour( bjour )
| |
− | jour = tonumber( bjour )
| |
− | if jour then
| |
− | if jour > 31 or jour < 1 then
| |
− | annee = jour
| |
− | jour = nil
| |
− | else
| |
− | return erreur( 'Date', 'jour seul : ' .. bjour )
| |
− | end
| |
− | else
| |
− | return erreur( 'Jour', bjour )
| |
− | end
| |
− | end
| |
− | end
| |
− | end
| |
− |
| |
− | -- vérification de l'absence d'un décalage
| |
− | if annee and annee < 13 and annee > 0 and not jour and ( tonumber( bmois ) or (not mois and tonumber( args[4] ) ) ) then
| |
− | return false, Outils.erreur( 'année improbable (' .. annee .. ')' )
| |
− | end
| |
− |
| |
− | local resultat = {
| |
− | jour = jour,
| |
− | mois = mois,
| |
− | numMois = numMois,
| |
− | annee = annee,
| |
− | masquerAnnee = args.masquerAnnee,
| |
− | masquerMois = args.masquerMois,
| |
− | }
| |
− | return true, resultat
| |
− | end
| |
− | | |
− | function fun.modeleDateAnalyseJMA( args )
| |
− | local function masquerParam( p ) -- sépare le signe moins final éventuel signifiant que le paramètre ne soit pas être affiché.
| |
− | local s
| |
− | if trim( p ) then
| |
− | p, s = p:match( '^(.-)(%-?)%s*$' )
| |
− | end
| |
− | return p, ( s == '-' or nil )
| |
− | end
| |
− |
| |
− | local test, resultat
| |
− | local arg1, arg2, arg3 = fun.nettoyageJour( args[1] ), trim( args[2] ), trim( args[3] )
| |
− | if type( arg1 ) == 'string' and arg3 == nil and ( arg1:match( '[^ ./-][ ./-]+[^ ./-]' ) or arg2 == nil or dataLiens[arg2] or mw.ustring.match( arg2, '%a %a' ) ) then
| |
− | -- la date est dans le premier paramètre
| |
− | test, resultat = fun.separationJourMoisAnnee( arg1 )
| |
− | if test then
| |
− | resultat.qualificatif = arg2
| |
− | end
| |
− | else
| |
− | local param, masquerM, masquerA
| |
− | param = { args[1] or args.jour }
| |
− | param[2], masquerM = masquerParam( args[2] or args.mois )
| |
− | param[3], masquerA = masquerParam( args[3] or args.annee or args['annee'] )
| |
− | param[4] = masquerParam( args[4] )
| |
− | test, resultat = fun.validationJourMoisAnnee( param )
| |
− | if test then
| |
− | resultat.masquerAnnee = masquerA
| |
− | resultat.masquerMois = masquerM
| |
− | resultat.qualificatif = trim( args[4] )
| |
− | end
| |
− | end
| |
− |
| |
− | return test, resultat
| |
− | end
| |
− | | |
− | ---
| |
− | -- émule le modèle {{m|Date}}.
| |
− | -- Paramètres :
| |
− | -- 1 : jour (numéro ou "1er"). optionnel, si absent pas de jour
| |
− | -- 2 : mois (en toutes lettres)
| |
− | -- 3 : année (nombre)
| |
− | -- 4 : optionnel, spécialité de l'année
| |
− | -- Comportement spécial ("truc à deux balles au lieu d'utiliser un
| |
− | -- paramètre nommé du genre "sans année=oui"...") : si 1 est vide
| |
− | -- mais que le reste est complet → on n'affiche pas l'année
| |
− | function fun.modeleDate( frame )
| |
− | local args = Outils.extractArgs( frame )
| |
− | local test, params = fun.modeleDateAnalyseJMA( args )
| |
− | local cat, resultat = ''
| |
− | if test then
| |
− | local listeParam = {
| |
− | qualificatif = 'qualificatif',
| |
− | age = 'âge',
| |
− | ['âge'] = 'âge',
| |
− | naissance = 'naissance',
| |
− | mort = 'mort',
| |
− | ['décès'] = 'mort',
| |
− | julien = 'julien',
| |
− | avJC = 'avJC',
| |
− | nolinks = 'nolinks',
| |
− | }
| |
− | for n, v in pairs( listeParam ) do
| |
− | params[v] = params[v] or args[n]
| |
− | end
| |
− | resultat = fun._modeleDate( params )
| |
− | | |
− | else
| |
− | local namespaceCategorisation = { [0] = true, [4] = true, [10] = true, [14] = true, [100] = true }
| |
− | if namespaceCategorisation[ mw.title.getCurrentTitle().namespace ] and not Outils.notEmpty( args.nocat ) then
| |
− | cat = '[[Catégorie:Page utilisant le modèle date avec une syntaxe erronée]]'
| |
− | end
| |
− | resultat = params .. cat
| |
− | end
| |
− | return resultat or ''
| |
− | end
| |
− | | |
− | function fun._modeleDate( args )
| |
− | local annee, mois, numMois, jour = args.annee, args.mois, args.numMois, args.jour
| |
− | local qualificatif = args.qualificatif
| |
− |
| |
− | if ( annee or mois or jour ) == nil then
| |
− | return
| |
− | end
| |
− |
| |
− | -- on traite l'age, naissance et mort
| |
− | local age = trim( args['âge'] or args['age'] )
| |
− | age = age and fun.age( annee, numMois, jour )
| |
− | local naissance = trim( args.naissance )
| |
− | local mort = trim( args.mort )
| |
− |
| |
− | -- on traite le calendrier
| |
− | local gannee, gmois, gjour = annee, numMois, jour -- date suivant le calendrier grégorien pour <time>
| |
− | local jannee, jmois, jjour = annee, mois, jour -- servira éventuellement à a affiché la date selon le calendrier julien
| |
− | local julien2, julien3 = nil, nil -- servira éventuellement à a affiché des parenthèses
| |
− | local julien = trim( string.lower( args.julien or '' ) )
| |
− | if annee and jour then
| |
− | local amj = annee * 10000 + numMois * 100 + jour
| |
− | if amj < 15821014 then
| |
− | if annee > 0 then
| |
− | gannee, gmois, gjour = fun.julianToGregorian( annee, numMois, jour )
| |
− | else
| |
− | -- calendrier grégorien proleptique avec année 0.
| |
− | gannee, gmois, gjour = fun.julianToGregorian( annee + 1, numMois, jour )
| |
− | end
| |
− | elseif julien == 'oui' then
| |
− | gannee, gmois, gjour = fun.julianToGregorian( annee, numMois, jour )
| |
− | annee, mois, jour = gannee, liste_mois[gmois][1], gjour
| |
− | end
| |
− | else
| |
− | if annee and annee < 0 then
| |
− | gannee = gannee + 1
| |
− | end
| |
− | end
| |
− |
| |
− |
| |
− | -- on génère le résultat
| |
− |
| |
− | -- Déclarations des variables
| |
− | local wikiListe = TableBuilder.new() -- reçois le texte affiché pour chaque paramètre
| |
− | local iso = TableBuilder.new() -- reçois le format date ISO de ce paramètre
| |
− |
| |
− | local dataQualificatif, dataCat
| |
− | if not args.nolinks then
| |
− | dataQualificatif = dataLiens[qualificatif or '']
| |
− | if type( dataQualificatif ) ~= 'table' then
| |
− | -- si le qualifiquatif n'est pas dans la base de donnée, on crée une table minimum,
| |
− | -- qui imposera un test sur l'annee, mais considère qu'il n'y a pas de lien sur le jour ou le mois
| |
− | dataQualificatif = { qualificatif = ' ' .. qualificatif, annee = { } }
| |
− | end
| |
− | dataCat = dataLiens[dataQualificatif.cat]
| |
− | if type( dataCat ) ~= 'table' or dataCat == dataQualificatif then
| |
− | dataCat = { qualificatif = '' }
| |
− | end
| |
− | end
| |
− | local function wikiLien( lien, texte )
| |
− | if lien == texte then
| |
− | return '[[' .. texte .. ']]'
| |
− | else
| |
− | return '[[' .. lien .. '|' .. texte .. ']]'
| |
− | end
| |
− | end
| |
− |
| |
− | -- Date julienne
| |
− | if jjour ~= jour then
| |
− | if jjour == 1 then
| |
− | jjour = '<abbr class="abbr" title="premier">1<sup>er</sup></abbr>'
| |
− | end
| |
− | if jannee ~= annee then
| |
− | julien3 = '(<abbr class=abbr title="selon le calendrier julien">' .. jjour .. ' ' .. jmois .. ' ' .. jannee .. '</abbr>)'
| |
− | else
| |
− | julien2 = '(<abbr class=abbr title="selon le calendrier julien">' .. jjour .. ' ' .. jmois .. '</abbr>)'
| |
− | end
| |
− | end
| |
− |
| |
− | | |
− | -- le jour si présent
| |
− | local qualifJour = ''
| |
− | if jour then
| |
− | local texteJour = jour
| |
− | if args.nolinks then
| |
− | if jour == 1 then
| |
− | jour = modelePremier
| |
− | end
| |
− | wikiListe.insert( jour )
| |
− | else
| |
− | qualifJour = dataQualificatif.jour and dataQualificatif.qualificatif
| |
− | or dataCat.jour and dataCat.qualificatif
| |
− | or ''
| |
− | local lien = jour .. ' ' .. mois .. ' ' .. qualifJour
| |
− | if jour == 1 then
| |
− | jour = '1<sup>er</sup>'
| |
− | lien = '1er ' .. mois .. ' ' .. qualifJour
| |
− | end
| |
− | -- s'il n'y a pas de lien sur le mois, il sera affiché avec le jour.
| |
− | wikiListe.insert( wikiLien( lien, jour ) )
| |
− | wikiListe.insert( wikiLien( lien, jour .. ' '.. mois ) )
| |
− | end
| |
− | iso.insert( 1, string.sub( '0' .. gjour, -2 ) )
| |
− | end
| |
− |
| |
− | -- le mois
| |
− | if mois then
| |
− | if #wikiListe == 0 and annee == nil then
| |
− | return mois
| |
− | end
| |
− | if args.nolinks then
| |
− | if not args.masquerMois then
| |
− | wikiListe.insert( mois )
| |
− | end
| |
− | else
| |
− | local lien
| |
− | if annee then
| |
− | lien = existDate( dataQualificatif, annee, mois ) or existDate( dataCat, annee, mois )
| |
− | if lien == nil and qualificatif and qualifJour == '' then
| |
− | -- test nouveau test sans le qualificatif uniquement s'il n'y a pas d'éphémérides pour ce qualificatif.
| |
− | lien = existDate( dataLiens[''], annee, mois )
| |
− | end
| |
− | end
| |
− | if lien or args.masquerMois then
| |
− | -- s'il y a un lien on retire le lien affichant 'jour mois' pour ajouter '[[mois annee|mois']]
| |
− | wikiListe.remove()
| |
− | if not args.masquerMois then
| |
− | wikiListe.insert( wikiLien( lien, mois ) )
| |
− | end
| |
− | elseif #wikiListe > 0 then
| |
− | -- sinon on retire le lien affichant 'jour' pour ne garder que le lien 'jour mois'
| |
− | wikiListe.remove( #wikiListe - 1 )
| |
− | elseif args.masquerAnnee then
| |
− | -- s'il n'y a pas de jour et que l'année n'est pas affichée, on insère le mois seul.
| |
− | wikiListe.insert( mois )
| |
− | end
| |
− | end
| |
− | if gmois then
| |
− | iso.insert( 1, string.sub( '0' .. gmois, -2 ) )
| |
− | end
| |
− | end
| |
− | if( julien2 ) then
| |
− | wikiListe.insert( julien2 )
| |
− | end
| |
− |
| |
− | -- l'année
| |
− | if annee then
| |
− | if not args.masquerAnnee then
| |
− | local texteAnnee = annee
| |
− | local lien
| |
− | if annee < 0 then
| |
− | local annneeAvJc = 0 - annee
| |
− | lien = lien or ( annneeAvJc .. ' av. J.-C.' )
| |
− | local avJC = trim( string.lower( args.avJC or '' ) )
| |
− | if args.avJC == 'non' then
| |
− | texteAnnee = annneeAvJc
| |
− | else
| |
− | texteAnnee = annneeAvJc .. ' <abbr class="abbr" title="'
| |
− | .. annneeAvJc .. ' avant Jésus-Christ">av. J.-C.</abbr>'
| |
− | end
| |
− | end
| |
− | if args.nolinks then -- seulement si on doit l'affichée
| |
− | wikiListe.insert( texteAnnee )
| |
− | else
| |
− | lien = existDate( dataQualificatif, annee ) or existDate( dataCat, annee ) or lien or annee
| |
− | if mois and #wikiListe == 0 then
| |
− | -- si le mois n'a pas de lien et n'est pas affiché avec le jour, il est affiché avec l'année.
| |
− | texteAnnee = mois .. ' ' .. texteAnnee
| |
− | end
| |
− | wikiListe.insert( wikiLien( lien, texteAnnee ) )
| |
− | end
| |
− | end
| |
− | if gannee > 999 then
| |
− | iso.insert( 1, gannee )
| |
− | elseif gannee > -1 then
| |
− | iso.insert( 1, string.sub( '000' .. gannee , -4 ) )
| |
− | elseif gannee > -999 then
| |
− | -- calendrier grégorien proleptique avec année 0.
| |
− | iso.insert( 1, 'U-' .. string.sub( '000' .. ( 0 - gannee ), -4 ) )
| |
− | else
| |
− | iso.insert( 1, 'U' .. gannee )
| |
− | end
| |
− | end
| |
− | if( julien3 ) then
| |
− | wikiListe.insert( julien3 )
| |
− | end
| |
− | | |
− |
| |
− | -- l'age
| |
− | if type( age ) == 'number' and age >= 0 and ( not naissance or age < 120 ) then
| |
− | if age == 0 then
| |
− | age = '(moins d’un an)'
| |
− | elseif age == 1 then
| |
− | age = '(1 an)'
| |
− | else
| |
− | age = '(' .. age .. ' ans)'
| |
− | end
| |
− | else
| |
− | age = false
| |
− | end
| |
− |
| |
− |
| |
− | -- compilation du résultat
| |
− | local wikiTexte = wikiListe.concat( ' ' )
| |
− | local isoTexte = iso.concat( '-' )
| |
− |
| |
− | -- On ajoute un peu de sémantique.
| |
− | local wikiHtml = mw.html.create( '' )
| |
− |
| |
− | local dateHtml = wikiHtml:tag( 'time' )
| |
− | :wikitext( wikiTexte )
| |
− | if wikiTexte:match( ' ' ) then
| |
− | dateHtml:addClass( 'nowrap' )
| |
− | end
| |
− | if isoTexte ~= wikiTexte then
| |
− | dateHtml:attr( 'datetime', isoTexte )
| |
− | end
| |
− | if not args.nolinks then
| |
− | dateHtml:addClass( 'date-lien' )
| |
− | end
| |
− | if naissance then
| |
− | dateHtml:addClass( 'bday' )
| |
− | elseif mort then
| |
− | dateHtml:addClass( 'dday' )
| |
− | end
| |
− | if age then
| |
− | wikiHtml:wikitext( ' ' )
| |
− | :tag( 'span' )
| |
− | :addClass( 'noprint')
| |
− | :wikitext( age )
| |
− | :done()
| |
− | end
| |
− |
| |
− | return tostring( wikiHtml )
| |
− | end
| |
− | | |
− | | |
− | ---
| |
− | -- fonction destinée aux infobox, notamment pour afficher les dates de naissance et de mort
| |
− | -- les liens présent dans les dates fournies sont automatiquement supprimées pour gérer les cas ou
| |
− | -- le paramètre contient déjà un modèle date.
| |
− | -- Paramètres :
| |
− | -- 1 : type de date à afficher (naissance / n, mort / m, ou date / d)
| |
− | -- 1 : Date ou date de naissance
| |
− | -- 2 : Date de mort si type n ou m
| |
− | -- qualificatif = suffixe des page de date à lier (exemple : en musique)
| |
− | -- nolinks : n'affiche pas de lien
| |
− | function fun.dateInfobox( frame )
| |
− | local args = frame.args
| |
− | if type( args ) ~= 'table' or not ( args[1] and args[2] ) then
| |
− | return
| |
− | end
| |
− |
| |
− | local function analyseDate( d )
| |
− | if trim( d ) then
| |
− | -- supprime les liens
| |
− | local analyse = d:match( ' ou ') or d:match( 'entre ' ) or d:match( 'vers ' ) or d:match( 'après ' ) or d:match( 'avant ' )
| |
− | if analyse then
| |
− | return d
| |
− | end
| |
− | analyse = d:match( 'datetime="([%d-]+)"' ) or d
| |
− | local debut, fin = analyse:match( '(.-%d%d%d%]*%-?)([\127 ].+)' )
| |
− | if not debut then
| |
− | debut, fin = analyse:match( '(.-%d%d%d%]*%-?)(<br ?/?>.+)' )
| |
− | end
| |
− | analyse = debut or analyse
| |
− | analyse = analyse:gsub( '%[%[([^%[%]|]*)|?([^%[%]]*)%]%]', function ( l, t ) return trim( t ) or l end )
| |
− | local t, r = fun.separationJourMoisAnnee( analyse )
| |
− | if t then
| |
− | return r, fin
| |
− | else
| |
− | return d, fin
| |
− | end
| |
− | end
| |
− | end
| |
− |
| |
− | local naissance = args[1]:match( '^n' )
| |
− | local mort = args[1]:match( '^m' ) or args[1]:match( 'décès' )
| |
− | local affichageDate, qualificatif = args[2], args[4]
| |
− | local affichageDateTab, resultatDate, complementDate
| |
− | local dateNaissance, dateMort
| |
− | if mort then
| |
− | affichageDate = args[3]
| |
− | end
| |
− | if not trim( affichageDate ) then
| |
− | return
| |
− | end
| |
− | if affichageDate:match( '</time>' ) then
| |
− | -- S'il y a des liens il y a probablement déjà un modèle date, évitons de l'exècuter une 2e fois
| |
− | if ( naissance or mort ) and ( affichageDate:match( 'wikidata%-linkback' )) then
| |
− | dateNaissance = analyseDate( args[2] )
| |
− | dateMort = analyseDate( args[3] )
| |
− | resultatDate = affichageDate
| |
− | else
| |
− | return affichageDate
| |
− | end
| |
− | else
| |
− | affichageDateTab, complementDate = analyseDate( affichageDate )
| |
− | if type( affichageDateTab ) ~= 'table' then
| |
− | return affichageDateTab
| |
− | else
| |
− | if naissance then
| |
− | dateNaissance = affichageDateTab
| |
− | dateMort = analyseDate( args[3] )
| |
− | elseif mort then
| |
− | dateNaissance = analyseDate( args[2] )
| |
− | dateMort = affichageDateTab
| |
− | else
| |
− | qualificatif = args[3]
| |
− | end
| |
− | affichageDateTab.naissance = naissance
| |
− | affichageDateTab.mort = mort
| |
− | affichageDateTab.qualificatif = args.qualificatif or qualificatif
| |
− | affichageDateTab.nolinks = args.nolinks
| |
− | affichageDateTab.nocat = args.nocat
| |
− | affichageDateTab.julien = args.julien
| |
− | end
| |
− | end
| |
− | resultatDate = resultatDate or fun.modeleDate( affichageDateTab )
| |
− |
| |
− | local age, prefixAge, suffixAge, calculAge = '', ' <span class="noprint">(', ')</span>', nil
| |
− | if naissance and dateNaissance and not dateMort and type( dateNaissance ) == 'table' then
| |
− | calculAge = fun.age( dateNaissance.annee, dateNaissance.numMois, dateNaissance.jour )
| |
− | if calculAge and calculAge > 120 then
| |
− | calculAge = nil
| |
− | end
| |
− | elseif mort and dateNaissance and dateMort and type( dateNaissance ) == 'table' and type( dateMort ) == 'table' then
| |
− | calculAge = fun.age( dateNaissance.annee, dateNaissance.numMois, dateNaissance.jour, dateMort.annee, dateMort.numMois, dateMort.jour )
| |
− | prefixAge = ' (à '
| |
− | suffixAge = ')'
| |
− | end
| |
− | if tonumber( calculAge ) then
| |
− | if calculAge > 1 then
| |
− | age = prefixAge .. calculAge .. ' ans' .. suffixAge
| |
− | elseif calculAge == 1 then
| |
− | age = prefixAge .. 'un an' .. suffixAge
| |
− | elseif calculAge == 0 then
| |
− | age = prefixAge .. 'moins d’un an' .. suffixAge
| |
− | end
| |
− | if complementDate and complementDate:match( 'ans?%)' ) then
| |
− | complementDate = ''
| |
− | end
| |
− | end
| |
− |
| |
− | return resultatDate .. ( complementDate or '' ) .. age
| |
− | end
| |
− | | |
− | | |
− | ---
| |
− | -- la fonction dateISO renvoie un date au format aaaa-mm-jj (sans liens)
| |
− | -- l'année peut être sous la forme 2013 ou [[2013 en litérature|2013]]
| |
− | -- le mois peut être en lettre ou en chiffres
| |
− | -- le jour peut être sous la forme '05', '{{1er}}' ou 'vendredi 13'
| |
− | function fun.dateISO( frame )
| |
− | local args = Outils.extractArgs( frame )
| |
− | local annee = Outils.notEmpty( args['année'], args.annee, args.year, args.date )
| |
− | -- extraction de l'année
| |
− | if type( annee ) == 'string' then
| |
− | annee = ( tonumber( annee ) -- match '2013'
| |
− | or string.match ( annee, '%D(%d%d%d%d)%D' ) -- match '[[2013 en musique|2013]]'
| |
− | or string.match ( annee, '%D(%d%d%d%d)$' ) -- match '17 septembre 2013'
| |
− | or string.match ( annee, '^(%d%d%d%d)%D' ) -- match '2013-09-17'
| |
− | )
| |
− | end
| |
− | annee = tonumber( annee )
| |
− |
| |
− | -- le format de date iso est défini suivant le calendrier grégorien.
| |
− | -- Avant l'année 1583 la date est calendrier est probablement du calendrier julien,
| |
− | -- donc autant s'abstenir.
| |
− | if annee and annee > 1582 then
| |
− | local mois = Outils.notEmpty( args.mois, args.month )
| |
− | -- num mois trouve le numéro du mois, qu'il soit numérique ou texte, complet ou abrégé.
| |
− | local nomMois, numMois = fun.determinationMois( mois )
| |
− | if numMois then
| |
− | mois = '-' .. string.sub( '0' .. numMois, -2 )
| |
− |
| |
− | local jour = Outils.notEmpty( args.jour, args.day, args['quantième'] )
| |
− | if type( jour ) == 'string' then
| |
− | jour = tonumber( jour ) or tonumber( string.match ( jour, '%d+') )
| |
− | end
| |
− | jour = tonumber( jour )
| |
− | if jour and jour <= liste_mois[numMois].nJour then
| |
− | jour = '-' .. string.sub( '0' .. jour, -2 )
| |
− | return annee .. mois .. jour
| |
− | else
| |
− | return annee .. mois
| |
− | end
| |
− | else
| |
− | return tostring( annee )
| |
− | end
| |
− | end
| |
− | end
| |
− | | |
− | ---
| |
− | -- Rang du jour dans l'année
| |
− | -- Usage : do_dayRank{année,mois,jour}
| |
− | function fun.do_dayRank(arguments)
| |
− | local yr = tonumber(arguments.year or arguments[1]) or 1
| |
− | local mt = tonumber(arguments.month or arguments[2]) or 1
| |
− | local dy = tonumber(arguments.day or arguments[3]) or 1
| |
− | -- Rangs des premiers des mois
| |
− | local ranks = {0,31,59,90,120,151,181,212,243,273,304,334}
| |
− |
| |
− | local rank = (ranks[mt] or 0) + dy - 1
| |
− | if(fun.isLeapYear(yr) and (mt >= 3)) then
| |
− | rank = rank+1
| |
− | end
| |
− | return rank
| |
− | end
| |
− | | |
− | -- Nombre de jours entre deux années (du 1er janvier au 1er janvier)
| |
− | -- Suit le calendrier grégorien
| |
− | function fun.do_daysBetween(arguments)
| |
− | local yr1 = tonumber(arguments[1]) or 0
| |
− | local yr2 = tonumber(arguments[2]) or 0
| |
− |
| |
− | return fun.daysSinceOrigin(yr2) - fun.daysSinceOrigin(yr1)
| |
− | end
| |
− | | |
− | -- Nombre de jours depuis l'année 1 (du 1er janvier au 1er janvier)
| |
− | function fun.daysSinceOrigin(year)
| |
− | local yr = year-1
| |
− | return 365*yr + math.floor(yr/4) - math.floor(yr/100) + math.floor(yr/400)
| |
− | end
| |
− | | |
− | -- Test d'année bissextile (Suit le calendrier grégorien)
| |
− | function fun.isLeapYear(year)
| |
− | local yr = tonumber(year) or 1
| |
− | return (yr%4 == 0) and ((yr%100 ~= 0) or (yr%400 == 0))
| |
− | end
| |
− | | |
− | -- Conversion d'un nombre en chiffres romains
| |
− | function fun.toRoman(number)
| |
− | local n = math.floor(number)
| |
− | local letters = {"I","V","X","L","C","D","M","",""}
| |
− | local pattern = {"","0","00","000","01","1","10","100","1000","02"}
| |
− | local result = ""
| |
− | if(n<=0 or n>=4000) then
| |
− | result = "---"
| |
− | else
| |
− | for i=1,7,2 do
| |
− | local p = pattern[n%10 + 1]
| |
− | for j=0,2 do
| |
− | p = string.gsub(p,tostring(j),letters[i+j])
| |
− | end
| |
− | result = p .. result
| |
− | n = math.floor(n/10)
| |
− | end
| |
− | end
| |
− | return result
| |
− | end
| |
− | | |
− | -- Conversion et affichage d'une date dans le calendrier républicain
| |
− | function fun.dateRepublicain(frame)
| |
− | local pframe = frame:getParent()
| |
− | local arguments = pframe.args
| |
− | return fun.formatRepCal(fun.do_toRepCal(arguments))
| |
− | end
| |
− | | |
− | ---
| |
− | -- Calcul d'une date dans le calendrier républicain
| |
− | -- On suppose que les années 4n+3 sont sextiles (3, 7, 11...)
| |
− | function fun.do_toRepCal(arguments)
| |
− | local yr = tonumber(arguments.year or arguments[1]) or 2000
| |
− | -- rang absolu du jour demandé, le jour 0 étant le 22 septembre 1792 (1er jour de l'an I)
| |
− | local repDays = fun.do_dayRank(arguments) + fun.do_daysBetween{1792,yr} - fun.do_dayRank{1792,9,22}
| |
− | local repYear = math.floor((repDays+731)/365.25) - 1
| |
− | local repDayRank = repDays - 365*(repYear-1) - math.floor(repYear/4)
| |
− | local repMonth, repDay = math.floor(repDayRank/30)+1, (repDayRank%30)+1
| |
− | return {repYear, repMonth, repDay}
| |
− | end
| |
− | | |
− | ---
| |
− | -- Formatage d'une date selon le calendrier républicain
| |
− | -- Usage : fun.formatRepCal{année,mois,jour}
| |
− | function fun.formatRepCal(arguments)
| |
− | local months = {"Vendémiaire","Brumaire","Frimaire","Nivôse","Pluviôse","Ventôse","Germinal","Floréal","Prairial","Messidor","Thermidor","Fructidor"}
| |
− | local extras = {"de la vertu","du génie","du travail","des récompenses","de l'opinion","de la révolution"}
| |
− | local result = ""
| |
− | if(arguments[2] < 13) then
| |
− | result = result .. tostring(arguments[3]) .. " " .. months[arguments[2]]
| |
− | else
| |
− | result = result .. "jour " .. extras[arguments[3]]
| |
− | end
| |
− | result = result .. " de l'an " .. fun.toRoman(arguments[1])
| |
− | return result
| |
− | end
| |
− | | |
− | ---
| |
− | -- Voir Modèle:Âge
| |
− | -- retourne l'age en fonction de la ou les dates fournies. La valeur retounée est de type 'number'
| |
− | -- Parammètres :
| |
− | -- 1, 2, 3 : année, mois jour de naissance (supposé dans le calendrier grégorien)
| |
− | -- 4, 5, 6 : année, mois, joue du calcul (facultatif, par défaut la date UTC courante).
| |
− | function fun.age( an, mn, jn, ac, mc, jc )
| |
− | if ac == nil then
| |
− | local today = os.date( '!*t' )
| |
− | ac = today.year
| |
− | mc = today.month
| |
− | jc = today.day
| |
− | else
| |
− | ac = tonumber( ac )
| |
− | mc = tonumber( mc )
| |
− | jc = tonumber( jc )
| |
− | end
| |
− | | |
− | local an = tonumber( an )
| |
− | local mn = tonumber( mn )
| |
− | local jn = tonumber( jn )
| |
− | | |
− | if an == nil or ac == nil or mn == nil or mc == nil then
| |
− | -- pas de message d'erreur qui risque de faire planter la fonction appelante
| |
− | -- à elle de gérer ce retour.
| |
− | return
| |
− | end
| |
− |
| |
− | local age = ac - an
| |
− | if mc == mn then
| |
− | if jc == nil or jn == nil then
| |
− | return
| |
− | end
| |
− | return age-tonumber( jc < jn and 1 or 0 )
| |
− | else
| |
− | return age-tonumber( mc < mn and 1 or 0 )
| |
− | end
| |
− | end
| |
− | | |
− | function fun.modeleAge( frame )
| |
− | local args = frame.getParent().args
| |
− | local age = fun.age (
| |
− | args[1] or args['année'],
| |
− | args[2] or args['mois'],
| |
− | args[3] or args['jour'],
| |
− | args[4],
| |
− | args[5],
| |
− | args[6]
| |
− | )
| |
− | if age then
| |
− | return age
| |
− | else
| |
− | return Outils.erreur("Paramètres incorrects ou insuffisants ou pour calculer l'âge précis" )
| |
− | end
| |
− | end
| |
− | | |
− | ---
| |
− | -- calcul du jour julien à partir d'une date du calendrier grégorien
| |
− | function fun.julianDay( year, month, day, hour, min, sec )
| |
− | local julian
| |
− | julian = math.floor( math.floor( ( year * 12 + month + 57609 ) / 12 - 1 ) * 1461 / 4 )
| |
− | - math.floor( math.floor( ( year * 12 + month + 57609 ) / 12 - 1 ) / 100 )
| |
− | + math.floor( math.floor( ( year * 12 + month + 57609 ) / 12 - 1 ) / 400 )
| |
− | + math.floor( ( math.fmod( month + 57609, 12 ) + 4 ) * 153 / 5 )
| |
− | + day + ( hour or 12 ) / 24 + ( min or 0 ) / 1440 + ( sec or 0 ) / 86400
| |
− | - 32167.5
| |
− | return julian
| |
− | end
| |
− | | |
− | ---
| |
− | -- calcul du jour julien à partir d'une date du calendrier julien
| |
− | function fun.julianDayJulian( year, month, day, hour, min, sec )
| |
− | local julian
| |
− | julian = math.floor( math.floor( ( year * 12 + month + 57609 ) / 12 - 1 ) * 1461 / 4 )
| |
− | + math.floor( ( math.fmod( month + 57609, 12 ) + 4 ) * 153 / 5 )
| |
− | + day + ( hour or 12 ) / 24 + ( min or 0 ) / 1440 + ( sec or 0 ) / 86400
| |
− | - 32205.5
| |
− | return julian
| |
− | end
| |
− | | |
− | ---
| |
− | -- calcul d'une date dans le calendrier grégorien à partir du jour julien
| |
− | function fun.julianDayToGregorian( julianDay )
| |
− | local base = math.floor( julianDay + 32044.5 ) -- 1 March -4800 (proleptic Gregorian date)
| |
− | local nCentury = math.floor( ( base * 4 + 3 ) / 146097 )
| |
− | local sinceCentury = base - math.floor( nCentury * 146097 / 4 )
| |
− | local nYear = math.floor( ( sinceCentury * 4 + 3 ) / 1461 )
| |
− | local sinceYear = sinceCentury - math.floor( nYear * 1461 / 4 )
| |
− | local nMonth = math.floor( ( sinceYear * 5 + 2 ) / 153 )
| |
− |
| |
− | local day = sinceYear - math.floor( ( nMonth * 153 + 2 ) / 5 ) + 1
| |
− | local month = nMonth - math.floor( nMonth / 10 ) * 12 + 3
| |
− | local year = math.floor( sinceYear / 306 ) + nYear + 100 * nCentury - 4800
| |
− |
| |
− | return year, month, day
| |
− | end
| |
− | | |
− | ---
| |
− | -- calcul d'une date dans le calendrier julien à partir du jour julien
| |
− | -- calcul basé sur l'algorythme de la page fr.wikipedia.org/wiki/Jour_julien (1/10/2013)
| |
− | function fun.julianDayToJulian( julianDay )
| |
− | local year = math.modf( ( julianDay * 4 - 6884469 ) / 1461 )
| |
− | local r2 = julianDay - math.modf( ( 1461 * year + 6884472 ) / 4 )
| |
− | local month = math.modf( ( 5 * r2 + 461 ) / 153 )
| |
− | local day = r2 - math.modf( ( 153 * month - 457 ) / 5 ) + 1
| |
− | if month > 12 then
| |
− | year = year + 1
| |
− | month = month - 12
| |
− | end
| |
− | return year, month, day
| |
− | end
| |
− | | |
− | ---
| |
− | -- calcul d'une date dans le calendrier grégorien à partir d'une date dans le calendrier julien
| |
− | function fun.julianToGregorian( year, month, day )
| |
− | return fun.julianDayToGregorian( fun.julianDayJulian( year, month, day ) )
| |
− | end
| |
− | | |
− | ---
| |
− | -- calcul d'une date dans le calendrier julien à partir d'une date dans le calendrier grégorien
| |
− | function fun.gregorianToJulian( year, month, day )
| |
− | year = tonumber(year)
| |
− | if month then month = tonumber(month) else month = 6 end --prend une valeur centrale pour donner un best "guess"
| |
− | if day then day = tonumber(day) else day = 15 end
| |
− | return fun.julianDayToJulian( fun.julianDay( year, month, day ) )
| |
− | end
| |
− | | |
− | | |
− | | |
− | ---
| |
− | -- erreurModuleData affiche d'un message d'erreur si le Module:Langue/Data n'a pas été chargé correctement,
| |
− | -- pour la page de discussion de la base de donnée et ceux qui veulent surveiller cette page.
| |
− | function fun.erreurModuleData()
| |
− | local success, resultat = pcall ( mw.loadData, 'Module:Date/Data' )
| |
− | if success == false then
| |
− | local message = [[<strong class="error">Le chargement du module Date/Data génère une erreur : </strong><br />%s<br />
| |
− | | |
− | <span class="error">Cette erreur doit être corrigée au plus vite car des milliers de page ne s'affichent pas correctement</span>
| |
− | ]]
| |
− | return string.format( message, resultat )
| |
− | end
| |
− | end
| |
− | | |
− | ---
| |
− | -- checkDataCat génère des liens vers les pages annuelles, mensuelles et d'éphémérides liè aux
| |
− | -- catégories du Module:Date/Data. La date la plus ancienne dépend de 'aucun' et 'seul[1]'
| |
− | -- Paramètres :
| |
− | -- 1 : la catégorie. Il y aura une section par qualificatif de cette catégorie.
| |
− | -- mois : oui pour avoir les liens vers les pages mensuelles et éphémérides (4 jours dans l'année)
| |
− | -- alias : pour avoir des lien pour les alias en plus des qualificatif
| |
− | function fun.checkDataCat( frame )
| |
− | local category = trim(frame.args[1])
| |
− | local monthLinks = frame .args.mois == 'oui'
| |
− | local alias = frame.args.alias == 'oui'
| |
− | local dataLink = mw.loadData( 'Module:Date/Data' )
| |
− | local wikiList = TableBuilder.new()
| |
− | local currentYear = tonumber( os.date( '%Y' ) )
| |
− | local columns = '<div style="-moz-column-width:5em;-webkit-column-width:5em;column-width:5em;-moz-column-gap:1em;-webkit-column-gap:1em;column-gap:1em;text-align:left;">'
| |
− | local newSection
| |
− | if monthLinks then
| |
− | newSection = '\n\n== %s ==\n\n=== Années ===\n' .. columns
| |
− | else
| |
− | newSection ='\n\n== %s ==\n' .. columns
| |
− | end
| |
− | for field, dataField in pairs( dataLink ) do
| |
− | -- boucle sur tous les qualificatif ayant pour catégorie le premier paramère
| |
− | if dataField.cat == category or ( category == 'cat' and dataField.cat == field ) then
| |
− | local monthInitialYear, initialYear
| |
− | -- définition de l'année à partir de laquelle on va tester toutes les année / mois
| |
− | if dataField.qualificatif == field or ( category == 'cat' and dataField.cat == field ) then
| |
− | if dataField.annee and dataField.annee.aucun and dataField.annee.aucun < currentYear then
| |
− | local aucun = ( dataField.annee.seul and dataField.annee.seul[1] ) or dataField.annee.aucun
| |
− | initialYear = math.min( aucun - math.ceil( (currentYear - aucun) / 4 ), currentYear - 50 )
| |
− | else
| |
− | initialYear = currentYear - 50
| |
− | end
| |
− | if dataField.mois and tonumber( dataField.mois.aucun ) and ( tonumber( dataField.mois.aucun ) < currentYear ) then
| |
− | local aucun = dataField.mois.aucun
| |
− | monthInitialYear = math.min( aucun - math.ceil( (currentYear - aucun) / 4 ), currentYear - 8 )
| |
− | else
| |
− | monthInitialYear = currentYear - 8
| |
− | end
| |
− | elseif alias then
| |
− | -- si le paramètre alias est défini on teste aussi tous les alias, sinon ils sont ignorés
| |
− | initialYear = currentYear - 50
| |
− | monthInitialYear = currentYear - 8
| |
− | end
| |
− |
| |
− | -- création de l'ensembles des liens
| |
− | if initialYear then
| |
− | -- ajout de lien vers les pages annuelles de l'année en court + 5 jusqu'à initialYear
| |
− | wikiList.insert( string.format( newSection, field ) )
| |
− | local fieldLink = ' ' .. field
| |
− | if category == 'cat' then
| |
− | fieldLink = ' ' .. dataField.qualificatif
| |
− | end
| |
− | for year = ( currentYear + 5 ), initialYear, -1 do
| |
− | wikiList.insert( '\n* [[' .. year .. fieldLink ..'|' .. year .. ']]' )
| |
− | end
| |
− | wikiList.insert( '\n</div>' )
| |
− |
| |
− | if monthLinks then
| |
− | -- insertstion de liens vers les mois de l'année en court + 1 jusqu'à monthInitialYear
| |
− | wikiList.insert( '\n\n=== Mois ===' )
| |
− | local month, sep
| |
− | for year = ( currentYear + 1 ), monthInitialYear, -1 do
| |
− | wikiList.insert( '\n* ' .. year .. ' : ' )
| |
− | sep = ' • '
| |
− | for j = 1, 12 do
| |
− | month = ucfirst( liste_mois[j][1] ) .. ' '
| |
− | if j == 12 then sep = ''
| |
− | end
| |
− | wikiList.insert( '[[' .. month .. year .. ' ' .. fieldLink .. '|' .. month .. ']]' .. sep )
| |
− | end
| |
− | end
| |
− |
| |
− | -- insertion de quelques date pour tester les éphémérides
| |
− | wikiList.insert( '\n\n=== Jours ===' )
| |
− | wikiList.insert( '\n* [[1er janvier ' .. fieldLink .. ']]' )
| |
− | wikiList.insert( '\n* [[14 mars ' .. fieldLink .. ']]' )
| |
− | wikiList.insert( '\n* [[22 juin ' .. fieldLink .. ']]' )
| |
− | wikiList.insert( '\n* [[3 septembre ' .. fieldLink .. ']]' )
| |
− | end
| |
− | end
| |
− | end
| |
− | end
| |
− |
| |
− | return table.concat( wikiList )
| |
− | end
| |
− | | |
− | --[[
| |
− | Cette fonction retourne "CET" ou "CEST" selon que dans la pseudo-timezone en cours
| |
− | c'est l'heure d'été ou l'heure d'hiver.
| |
− | Cette fonction n'a de sens a priori que pour des modèles utilisés en Europe
| |
− |
| |
− | Paramètre optionnel non nommé : "sans lien" : retourne le texte CET/CEST. sinon
| |
− | retourne ce même texte avec un wikilien vers les articles correspondant
| |
− | --]]
| |
− | function fun.CEST(frame)
| |
− | -- option : ne pas créer de wikilien
| |
− | local opt = trim(frame.args[1] or frame:getParent().args[1])
| |
− | -- on récupère l'information dans la zone courante
| |
− | local t = mw.getContentLanguage():formatDate("I", nil, true)
| |
− |
| |
− | if (t == "1") then -- heure d'été
| |
− | if (opt == "sans lien") then
| |
− | return "CEST"
| |
− | elseif (opt == "décalage") then
| |
− | return "2"
| |
− | else
| |
− | return "[[Heure d'été d'Europe centrale|CEST]]"
| |
− | end
| |
− | else -- heure d'hiver (ou autre zone où ça ne s'applique pas)
| |
− | if (opt == "sans lien") then
| |
− | return "CET"
| |
− | elseif (opt == "décalage") then
| |
− | return "1"
| |
− | else
| |
− | return "[[Heure normale d'Europe centrale|CET]]"
| |
− | end
| |
− | end
| |
− | end
| |
− | | |
− | return fun
| |