Module:TimeZone
跳到导航
跳到搜索
- local module = {}
- function module.getTimeZone(frame)
- local hour, minute = normalize(frame.args[1])
- local timezone = timeZoneToString(hour, minute)
- local output = frame.args["output"]
- if output == "number" then
- return timezone
- elseif output == "utc" then
- return "UTC"..timezone
- elseif output == "text" then
- if timezone == "+00:00" then
- return "零时区"
- else
- local left, middle
- --当时间差超过±12小时,在计算时区是必须调整至±12小时的范围内。
- local hour = math.fmod(hour, 24)
- local abs_hour = math.abs(hour)
- local sign = hour / abs_hour
- if abs_hour > 12 or (abs_hour == 12 and minute > 0) then
- hour = 24 - abs_hour
- if minute ~= 0 then
- hour = hour - 1
- minute = 60 - minute
- end
- hour = -sign * hour
- end
- if hour < 0 then
- left = "西"
- else
- left = "东"
- end
- local texts = {"一","二","三","四","五","六","七","八","九","十","十一","十二"}
- middle = texts[math.abs(tonumber(hour))]
- return left..middle.."区"
- end
- end
- end
- function module.convert(frame)
- local args = frame.args
- local year = tonumber(args["year"])
- local month = tonumber(args["month"])
- local day = tonumber(args["day"])
- local hour = tonumber(args["hour"]) or 12
- local minute = tonumber(args["minute"]) or 0
- local second = tonumber(args["second"]) or 0
- local o_hour, o_minute = normalize(args["o_timezone"])
- local c_hour, c_minute = normalize(args["c_timezone"])
- local o_sign, c_sign
- if o_hour >= 0 then o_sign = 1 else o_sign = -1 end
- if c_hour >= 0 then c_sign = 1 else c_sign = -1 end
- local difftime = (c_hour * 3600 + o_sign * c_minute * 60) -
- (o_hour * 3600 + c_sign * o_minute * 60)
- local o_time = { year = year, month = month, day = day, hour = hour, min = minute, sec = second }
- local c_time = os.date("*t", os.time(o_time) + difftime)
- local text = args[1] or ""
- --剥离nowiki标签。
- text = mw.text.unstripNoWiki(text)
- text = mw.text.decode(text)
- --格式化日期
- c_time['timezone'] = {c_hour, c_minute}
- text = formatDate(text, c_time)
- --生成能解析wiki文本的字符串。
- text = frame:preprocess(text)
- return text
- end
- function module.formatList(frame)
- local var_array = require("Module:Var-array")
- local formatList = {}
- for i, item in ipairs(getFormat()) do
- table.insert(formatList, { item.format, item.description })
- end
- var_array.new("timezone.convert.formatlist", formatList)
- end
- function getFormat()
- return {
- {
- format = "%(y)",
- description = "不包含纪元的年份。如果不包含纪元的年份小于10,则显示不具有前导零的年份。",
- callback = function(matched_times, time) return tostring(tonumber(string.sub(tostring(time.year), -2))) end
- },
- {
- format = "%y",
- description = "不包含纪元的年份。如果不包含纪元的年份小于10,则显示不具有前导零的年份。<code>%(y)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(string.sub(tostring(time.year), -2))) end
- },
- {
- format = "%(yy)",
- description = "不包含纪元的年份。如果不包含纪元的年份小于10,则显示具有前导零的年份。",
- callback = function(matched_times, time) return string.format("%02d", tonumber(string.sub(tostring(time.year), -2))) end
- },
- {
- format = "%(yyyy)",
- description = "包括纪元的四位数的年份。",
- callback = function(matched_times, time) return tostring(time.year) end
- },
- {
- format = "%(gg)",
- description = "时期或纪元。如果要设置格式的日期不具有关联的时期或纪元字符串,则忽略该模式。",
- callback = function(matched_times, time) return tostring((tonumber(time.year) - tonumber(string.sub(tostring(time.year), -2))) / 100) end
- },
- {
- format = "%(M)",
- description = "月份数字。一位数的月份没有前导零。",
- callback = function(matched_times, time) return tostring(tonumber(time.month)) end
- },
- {
- format = "%M",
- description = "月份数字。一位数的月份没有前导零。<code>%(M)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(time.month)) end
- },
- {
- format = "%(MM)",
- description = "月份数字。一位数的月份有一个前导零。",
- callback = function(matched_times, time) return string.format("%02d", (tonumber(time.month))) end
- },
- {
- format = "%(MMM)",
- description = "月份的缩写名称。",
- callback = function(matched_times, time)
- local AbbreviatedMonthNames = { "一", "二", "三", "四", "五", "六", "七", "八", "九", "十", "十一", "十二" }
- return AbbreviatedMonthNames[tonumber(time.month)]
- end
- },
- {
- format = "%(MMMM)",
- description = "月份的缩写名称。",
- callback = function(matched_times, time)
- local AbbreviatedMonthNames = { "一", "二", "三", "四", "五", "六", "七", "八", "九", "十", "十一", "十二" }
- return AbbreviatedMonthNames[tonumber(time.month)].."月"
- end
- },
- {
- format = "%(D)",
- description = "年中的某一天。",
- callback = function(matched_times, time)
- t1 = { year = time.year, month = time.month, day = time.day, hour = 0, min = 0, sec = 0 }
- t2 = { year = time.year, month = 1, day = 1, hour = 0, min = 0, sec = 0 }
- return tostring(math.floor(os.difftime(os.time(t1), os.time(t2)) / 86400))
- end
- },
- {
- format = "%D",
- description = "年中的某一天。<code>%(D)</code>的简略写法。",
- callback = function(matched_times, time)
- t1 = { year = time.year, month = time.month, day = time.day, hour = 0, min = 0, sec = 0 }
- t2 = { year = time.year, month = 1, day = 1, hour = 0, min = 0, sec = 0 }
- return tostring(math.floor(os.difftime(os.time(t1), os.time(t2)) / 86400))
- end
- },
- {
- format = "%(DD)",
- description = "这一年共有多少天。",
- callback = function(matched_times, time)
- t1 = { year = time.year + 1, month = 1, day = 1, hour = 0, min = 0, sec = 0 }
- t2 = { year = time.year, month = 1, day = 1, hour = 0, min = 0, sec = 0 }
- return tostring(math.floor(os.difftime(os.time(t1), os.time(t2)) / 86400))
- end
- },
- {
- format = "%(d)",
- description = "月中的某一天。一位数的日期没有前导零。",
- callback = function(matched_times, time) return tostring(tonumber(time.day)) end
- },
- {
- format = "%d",
- description = "月中的某一天。一位数的日期没有前导零。<code>%(d)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(time.day)) end
- },
- {
- format = "%(dd)",
- description = "月中的某一天。一位数的日期有一个前导零。",
- callback = function(matched_times, time) return string.format("%02d", tonumber(time.day)) end
- },
- {
- format = "%(w)",
- description = "周中的某一天。",
- callback = function(matched_times, time) return tostring(tonumber(time.wday)) end
- },
- {
- format = "%w",
- description = "周中的某一天。<code>%(w)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(time.wday)) end
- },
- {
- format = "%(ww)",
- description = "周中某天的缩写名称。",
- callback = function(matched_times, time)
- local wday = tonumber(time.wday)
- return mw.ustring.sub("日一二三四五六", wday, wday)
- end
- },
- {
- format = "%(www)",
- description = "周中某天的缩写名称。",
- callback = function(matched_times, time)
- local wday = tonumber(time.wday)
- return "星期"..mw.ustring.sub("日一二三四五六", wday, wday)
- end
- },
- {
- format = "%(h)",
- description = "12 小时制的小时。一位数的小时数没有前导零。",
- callback = function(matched_times, time) return tostring(math.fmod(tonumber(time.hour), 12)) end
- },
- {
- format = "%h",
- description = "12 小时制的小时。一位数的小时数没有前导零。<code>%(h)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(math.fmod(tonumber(time.hour), 12)) end
- },
- {
- format = "%(hh)",
- description = "12 小时制的小时。一位数的小时数有一个前导零。",
- callback = function(matched_times, time) return string.format("%02d", math.fmod(tonumber(time.hour), 12)) end
- },
- {
- format = "%(H)",
- description = "24 小时制的小时。一位数的小时数没有前导零。",
- callback = function(matched_times, time) return tostring(tonumber(time.hour)) end
- },
- {
- format = "%H",
- description = "24 小时制的小时。一位数的小时数没有前导零。<code>%(H)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(time.hour)) end
- },
- {
- format = "%(HH)",
- description = "24 小时制的小时。一位数的小时数有一个前导零。",
- callback = function(matched_times, time) return string.format("%02d", tonumber(time.hour)) end
- },
- {
- format = "%(m)",
- description = "分钟。一位数的分钟数没有前导零。",
- callback = function(matched_times, time) return tostring(tonumber(time.min)) end
- },
- {
- format = "%m",
- description = "分钟。一位数的分钟数没有前导零。<code>%(m)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(time.min)) end
- },
- {
- format = "%(mm)",
- description = "分钟。一位数的分钟数有一个前导零。",
- callback = function(matched_times, time) return string.format("%02d", tonumber(time.min)) end
- },
- {
- format = "%(s)",
- description = "秒。一位数的秒数没有前导零。",
- callback = function(matched_times, time) return tostring(tonumber(time.sec)) end
- },
- {
- format = "%s",
- description = "秒。一位数的秒数没有前导零。<code>%(s)</code>的简略写法。",
- callback = function(matched_times, time) return tostring(tonumber(time.sec)) end
- },
- {
- format = "%(ss)",
- description = "秒。一位数的秒数有一个前导零。",
- callback = function(matched_times, time) return string.format("%02d", tonumber(time.sec)) end
- },
- {
- format = "%(sss)",
- description = "Unix时间戳(Unix timestamp)。从格林威治时间1970年01月01日00时00分00秒起至现在的总秒数。",
- callback = function(matched_times, time) return tostring(os.time(time)) end
- },
- {
- format = "%(t)",
- description = "一天中时间段的更加详细的提示信息。",
- callback = function(matched_times, time)
- local hour = tonumber(time.hour)
- if hour < 12 then return "上午"
- else return "下午"
- end
- end
- },
- {
- format = "%t",
- description = "一天中时间段的更加详细的提示信息。<code>%(t)</code>的简略写法。",
- callback = function(matched_times, time)
- local hour = tonumber(time.hour)
- if hour < 12 then return "上午"
- else return "下午"
- end
- end
- },
- {
- format = "%(tt)",
- description = "一天中时间段的更加详细的提示信息。",
- callback = function(matched_times, time)
- local hour = tonumber(time.hour)
- if hour < 7 then return "凌晨"
- elseif hour < 11 then return "上午"
- elseif hour < 13 then return "中午"
- elseif hour < 17 then return "下午"
- elseif hour < 20 then return "傍晚"
- elseif hour < 22 then return "晚上"
- else return "深夜"
- end
- end
- },
- {
- format = "%(z)",
- description = "时区偏移量(“+”或“-”后面仅跟小时)。一位数的小时数没有前导零。例如,太平洋标准时间是“-8”。",
- callback = function(subStr, time)
- local hour, minute = time.timezone[1], time.timezone[2]
- if hour >= 0 then return "+"..hour
- else return tostring(hour)
- end
- end
- },
- {
- format = "%z",
- description = "时区偏移量(“+”或“-”后面仅跟小时)。一位数的小时数没有前导零。例如,太平洋标准时间是“-8”。<code>%(z)</code>的简略写法。",
- callback = function(subStr, time)
- local hour, minute = time.timezone[1], time.timezone[2]
- if hour >= 0 then return "+"..hour
- else return tostring(hour)
- end
- end
- },
- {
- format = "%(zz)",
- description = "时区偏移量(“+”或“-”后面仅跟小时)。一位数的小时数有前导零。例如,太平洋标准时间是“-08”。",
- callback = function(subStr, time)
- local hour, minute = time.timezone[1], time.timezone[2]
- if hour >= 0 then return string.format("+%02d", hour)
- else return string.format("-%02d", -hour)
- end
- end
- },
- {
- format = "%(zzz)",
- description = "完整时区偏移量(“+”或“-”后面跟有小时和分钟)。一位数的小时数和分钟数有前导零。例如,太平洋标准时间是“-08:00”。",
- callback = function(subStr, time)
- mw.log('zzzzz')
- return timeZoneToString(time.timezone[1], time.timezone[2])
- end
- },
- {
- format = "%(%)",
- description = "表示字符“%”。",
- callback = function(matched_times, time) return "%" end
- },
- {
- format = "%%",
- description = "表示字符“%”。<code>%(%)</code>的简略写法。",
- callback = function(matched_times, time) return "%" end
- }
- }
- end
- function formatDate(text, timeInfo)
- local FormatString = require("Module:FormatString")
- local tree = FormatString.buildTrie(getFormat())
- text = FormatString.replaceStr(text, tree, timeInfo)
- return text
- end
- function normalize(timezone)
- if timezone == nil or #timezone == 0 then
- return currentTimeZone() --用户当前时区
- else
- local hour, minute = mw.ustring.match(mw.text.trim(timezone), "^([-%+]?%d+):?(%d*)$")
- if hour == nil then
- error("时区参数格式不正确。")
- end
- return tonumber(hour), tonumber(minute) or 0
- end
- end
- function currentTimeZone()
- -- 2020.12.19: 由于服务端未知改动,本函数功能已失效,将默认返回表示东八区的时区信息。
- if true then
- return 8, 0
- else
- local a = os.date('!*t',os.time())--中时区的时间
- local b = os.date('*t',os.time())
- local seconds = os.difftime(os.time(b), os.time(a))
- local hour = math.floor(math.abs(seconds) / 3600)
- local minute = math.floor((math.abs(seconds) - hour * 3600) / 60)
- if seconds < 0 then
- hour = -hour
- if minute ~= 0 then
- minute = 60 - minute
- end
- end
- return hour, minute
- end
- end
- function timeZoneToString(hour, minute)
- if minute == nil then minute = 0 end
- if hour >= 0 then
- return mw.ustring.format("+%02d:%02d", hour, minute)
- else
- return mw.ustring.format("-%02d:%02d", math.abs(hour), minute)
- end
- end
- return module