Mobile Friendly Checklists - edmozley/freeitsm GitHub Wiki
Scope: all four pages — the list, the editor, settings, and the guide. Layers:
mobile.cssLAYERS 40-40e, andmobile.jsLAYERS 40c-40e (the editor's footer, and the list's filter sheet). Parent: Mobile‑Friendly · Techniques: §9, §14, §30, §32
Checklists is the first module contributed from outside the project, and it was built with mobile.css already linked on every page. Three of its four pages therefore measured clean before anything was done to them, which is a genuinely good starting position and also the reason two faults went unnoticed for a release.
What was missing was not rules but scoping: not one of the four pages carried a data-mobile-page marker, so nothing in mobile.css could be aimed at the module even if it had needed to be.
<style> block:
<link rel="stylesheet" href="../assets/css/mobile.css?v=148"> <!-- line 71 -->
<style> .chk-layout { display: flex; height: calc(100vh - 48px); } </style>That is §9 exactly — every same‑specificity rule in mobile.css loses on document order — and it is easy to miss precisely because the link is there. A page with no link at all announces itself; a page with the link in the wrong place looks done.
🔑 "
mobile.cssis linked" is not the check. "mobile.cssis linked after the page's own stylesheet" is.
This is the useful part of the round, and it is written up in full as Techniques §32.
.chk-card left=296 w=340 <- first card starts 296px in, on a 360px screen
main.chk-main w=100 <- the pane holding it
-
The grid has a floor.
repeat(auto-fill, minmax(340px, 1fr))reads as at least 340px, soauto-filllays out a 340px track on a 360px screen and the cards overflow. A real fault — fixed first, and it changed nothing measurable. -
Because the pane was already 100px.
.chk-layoutis a flex row whose 260px sidebar carriesflex-shrink: 0, leaving.chk-mainone hundred pixels wide. A1frtrack inside 100px is 100px. This is the fixed‑sidebar shape for the fifth time in the rollout, and the treatment is the usual one: stack, cap the sidebar, hand the scroller role to the main pane explicitly. -
And the card still would not shrink. With the track at
1frinside a full‑width pane,.chk-cardmeasured 489px in a 336px track — because a grid item hasmin-width: autojust as a flex item does (§14). The track was right and the item ignored it.
⭐ The lesson is the order, not any of the three rules. When a fix that should have moved something moves nothing, look outward before you look again at the rule you just wrote. §9 teaches this for load order; a correct rule inside a container that is already the wrong size behaves identically.
| All four pages |
data-mobile-page markers added (checklists, checklists-help, checklists-edit, checklists-settings) |
| Three pages |
mobile.css moved below the page's own <style>
|
| List page | layout stacks, sidebar capped at 32vh with the house 12px padding, .chk-main given the scroller role, grid to one column, card allowed to shrink |
| Settings, guide | nothing — they measured clean and still do |
| List page, round two | the scope panel became a sheet and the step role badges stopped spilling — see below |
| Editor | measured clean, then gained a sticky footer and the 16px rule — see below |
Desktop control at 1400px, run after moving the stylesheet because moving a stylesheet changes the cascade: flex row, 260px sidebar with its right border and 20px padding, main at 28px/36px, grid three 342px columns, card min-width: auto — all untouched.
Both faults here came from the same place: the module was written by somebody following the pattern from the outside, and the pattern's two invisible parts are the marker and the link's position. Neither shows up in a screenshot, and one of them makes the whole stylesheet silently lose ties.
- Grep for
data-mobile-pageon every new page, not formobile.css. - Check the link is after the page's
<style>. - Then measure — three of these four pages needed nothing, and knowing that quickly is worth more than guessing at rules.
Back and Save move to a sticky footer as icons (Ed). The top bar carried Back, the title, an unsaved-changes flag and Save, which at 360px left the title almost nothing - and Save is the control you reach for after scrolling to the bottom of a long template, the far end of the page from where it lived.
The real nodes are relocated, not copied: #edSave has a click handler bound in the page's own script and #edBack is an <a> carrying the href, so a clone would be a control that does nothing beside an original that still works. Each one's own label is harvested into aria-label, because an icon with no text has no accessible name, and everything is restored exactly above 768px.
Tapping Search templates zoomed the page. .chk-search is 13px, and §3 is unambiguous about what that costs:
iOS zooms on focus for any field under 16px → the page spills wider than the screen → Safari reflows the layout to a desktop width → the whole
max-width: 768pxblock stops matching.
So the symptom is not a bit of zoom, it is every mobile rule switching off at once. Fixed for the module rather than the one box: there are 21 focusable fields across these pages and the next one added would inherit the fault. No TinyMCE here, so the pointer: coarse content_style case does not arise.
Verified at 360x740: 21 fields, none under 16px, the search box exactly 16.
Both from Ed, using it.
The teal pill on each step — a suggested role, reading things like Tier 2 support — was pushing the page sideways.
.chk-step-row a tick · the step title · the role badge (space-between)
.chk-step-role white-space: nowrap
.chk-step-main min-width: (auto) <- the fault
§14 again: a flex item's automatic minimum is its content width, so the title would not shrink and the badge was pushed past the card's edge. The badge now drops to its own line, indented under the title — a role is a property of the step, not a continuation of its name, and at 336px there is no arrangement that fits both on one line.
⚠️ Those rows are styled INLINE, and an inline style beats any selector without!important. See §9's note on!importantfor the third option that was taken here: the markup was given three class names and nothing else changed, so desktop renders identically and the mobile layer has something to aim at.
A New button, a search box and three filter groups — scope, categories, roles — is most of a phone screen before a single template is shown. §4: a crowded panel gets its own screen. A Filters button in a sticky footer opens it full‑screen.
The real .chk-sidebar is relocated in and out, not cloned — the calendar's 16a move — and here the reason is concrete: the filter links call setScopeFilter(..., this) with this, and the active‑link bookkeeping walks .scope-link / .cat-link / .role-link. Two copies would be two sets of links disagreeing about which one is active.
🔑 The sheet closes on a filter tap and not on a search keystroke. A filter is an arrival — you have chosen, and the thing you chose is behind the sheet. A keystroke is not. The System Wiki round is why that distinction is written down: closing on every tap there would have made a whole branch of the tree unreachable.
Verified by driving it at 360×740: 20 step rows with zero badges past the edge, one sidebar copy, the sheet full‑screen when open and display: none when closed, still open after typing in search, and a tap on Task both closed it and took the list from 5 cards to 3. Desktop at 1400px: no sheet, no bar, sidebar still in the layout, step rows back to nowrap.
Both from Ed. The padding: the editor was still on the desktop's 24px/32px page padding with 20px/22px inside each card, so a field started 54px in from each edge of a 360px screen (card measured x=32, w=296). Now the house 12px outside and 14px inside - x=12, w=336.
The step rows: drag handle, number, title, role and delete were one flex row, and at 360px that measured a 77px title and a 54px role drop-down - neither readable. The row wraps, the title takes the rest of the first line, and the role drops to its own full line (280px) via order, so the markup the drag-and-drop code builds and re-reads is untouched. The toggles lose their 28px desktop indent so they line up with the role above them. Desktop at 1100px: same 24px/32px padding, title and role still on one row.
Checklists calls t() in PHP but never loads i18n.js and never exports window.translations, so window.t does not exist on these pages and the client‑side strings are hard‑coded English. Pre‑existing — the labels added here fall back to English to match rather than inventing a second mechanism — but it is a real gap if the module is ever to be translated.
-
assets/css/mobile.css(LAYERS 40, 40b, 40c, 40d) andassets/js/mobile.js(LAYER 40c - the editor's footer). - Pages:
checklists/index.php,checklists/edit/,checklists/settings/,checklists/help.php. - Changelog: #1770-#1772.
- Parent: Mobile‑Friendly · Siblings: Mobile: Tickets, Mobile: Knowledge.