Module:Current events calendar/sandbox
From Thetacola Wiki
Jump to navigationJump to search
Documentation for this module may be created at Module:Current events calendar/sandbox/doc
-- This module renders the calendar seen on [[Portal:Current events]]. --[[ Incoming expected variables: frame.args.year = Integer value for year frame.args.month = Integer value for month, 1 based. --]] local p = {} local function makeWikilink(link, display) if display then return string.format('[[%s|%s]]', link, display) else return string.format('[[%s]]', link) end end local function getDateStuff(argsDate) --[[ Note: This function takes advantage of the formatDate's second argument to create data for the archival calendars. If the second arg (argsDate) is nil, then formatDate assumes the current date/time. --]] local lang = mw.language.getContentLanguage() local firstOfMonth = lang:formatDate('01-m-Y', argsDate) return { argsDate = argsDate, year = tonumber(lang:formatDate('Y', argsDate)), month = lang:formatDate('F', argsDate), monthAndYear = lang:formatDate('F Y', argsDate), previousMonthAndYear = lang:formatDate('F Y', firstOfMonth .. ' -1 month'), nextMonthAndYear = lang:formatDate('F Y', firstOfMonth .. ' +1 month'), day = tonumber(lang:formatDate('j', argsDate)), daysInMonth = tonumber(lang:formatDate('j', firstOfMonth .. ' +1 month -1 day')), -- Weekday of the first day of the month -- Make compatible with Lua tables so we add 1. Sunday = 1, Saturday = 7. firstWeekday = tonumber(lang:formatDate('w', firstOfMonth)) + 1 } end local function isLinkworthy(day, currentDay) -- Returns true if the calendar day should be linked, and false if not. Days -- should be linked if they are the current day or if they are within the six -- preceding days, as that is the number of items on the current events page. return currentDay - 6 <= day and day <= currentDay end local function makeDayStrings(dateStuff) local calStrings = {} local currentDay = dateStuff.day local currentMonth = dateStuff.month local currentYear = dateStuff.year for day = 1, dateStuff.daysInMonth do if dateStuff.argsDate or isLinkworthy(day, currentDay) then table.insert(calStrings, string.format( "[[#%d %s %d|%d]]", currentYear, currentMonth, day, day )) else table.insert(calStrings, tostring(day)) end end return calStrings end local function export(dayStrings, dateStuff) -- Generates the calendar HTML. local monthAndYear = dateStuff.monthAndYear local root = mw.html.create('table') root :addClass('current-events-calendar') -- Make the table-layout-based Archive pages look good. When the Archives -- have been converted to a grid-based layout, this logic can be removed, -- and the corressponding CSS margin attribute can be simplified. :addClass(dateStuff.argsDate and 'current-events-calendar-archive') -- Headings :tag('caption') :tag('span') :addClass('noprint') :wikitext(makeWikilink( 'Portal:Current events/' .. dateStuff.previousMonthAndYear, '◀' )) :done() :tag('span') :wikitext(makeWikilink( 'Portal:Current events/' .. monthAndYear, monthAndYear )) :done() :tag('span') :addClass('noprint') :wikitext(makeWikilink( 'Portal:Current events/' .. dateStuff.nextMonthAndYear, '▶' )) -- Day of week headings local dayHeadingRow = root:tag('tr') local weekdays = {'S', 'M', 'T', 'W', 'T', 'F', 'S'} for _, weekday in ipairs(weekdays) do dayHeadingRow:tag('th'):wikitext(weekday) end -- Days -- Tracks the number of day cells. Negative values used for initial blank cells. local cellCount = 1 - dateStuff.firstWeekday while cellCount < #dayStrings do -- Weekly rows local weeklyRow = root:tag('tr') for i = 1, 7 do -- Always make 7 cells. cellCount = cellCount + 1 -- Use a blank cell if there is no corresponding dateString local dayString = dayStrings[cellCount] or '' weeklyRow:tag('td'):wikitext(dayString) end end -- Footer if not dateStuff.argsDate then -- No footer necessary on Archive pages. root:tag('tr') :addClass('current-events-calendar-footer') :addClass('noprint') :tag('td') :attr('colspan', '7') :wikitext(makeWikilink( 'Portal:Current events/' .. monthAndYear, 'More ' .. monthAndYear .. ' events... ' )) end return tostring(root) end function p.main(frame) local argsDate = nil if frame and frame.args and frame.args.year and frame.args.month then -- If a date is passed in, assume that the display page is an Archive page. -- If no date passed in, assume that the display page is the current Current Events page -- Construct a date, YYY-M-DD format. argsDate = frame.args.year .. "-" .. frame.args.month .. "-01" end local dateStuff = getDateStuff(argsDate) return frame:extensionTag{ name = 'templatestyles', args = { src = 'Module:Current events calendar/styles.css' } } .. export(makeDayStrings(dateStuff), dateStuff) end return p