Skip to content

Commit 49ebe62

Browse files
jeremymanningclaude
andcommitted
Fix personnel list two-column formatting
Target the existing columns-2 divs generated by tex4ht and wrap their text content in span elements so CSS grid can lay them out in two columns. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
1 parent 9893674 commit 49ebe62

File tree

1 file changed

+22
-75
lines changed

1 file changed

+22
-75
lines changed

checklist.js

Lines changed: 22 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -88,87 +88,34 @@ function fixEnumerationNumbering() {
8888
}
8989

9090
// Format personnel lists (lab members) into two-column grid layout
91-
// tex4ht generates text nodes directly in divs, but CSS grid needs child elements
91+
// tex4ht generates text nodes directly in divs with class "columns-2"
92+
// CSS grid needs child elements, so we wrap each name in a span
9293
function formatPersonnelLists() {
93-
// Find the lab members heading
94-
var labMembersHeading = null;
95-
var h2s = document.querySelectorAll('h2');
96-
h2s.forEach(function(h2) {
97-
if (h2.textContent.toLowerCase().includes('lab members')) {
98-
labMembersHeading = h2;
99-
}
100-
});
94+
// Find all columns-2 divs (tex4ht generates these for the \begin{columns} environment)
95+
var columnsDivs = document.querySelectorAll('div.columns-2');
10196

102-
if (!labMembersHeading) return;
97+
columnsDivs.forEach(function(div) {
98+
// Get the text content and split into individual names
99+
var text = div.textContent || '';
103100

104-
// Find all h3 elements after the lab members heading (subsections like "Graduate students")
105-
var sibling = labMembersHeading.nextElementSibling;
106-
while (sibling) {
107-
// Stop if we hit another h2 (new major section)
108-
if (sibling.tagName === 'H2') break;
109-
110-
if (sibling.tagName === 'H3') {
111-
// Find the content after this h3 that contains personnel names
112-
var contentSibling = sibling.nextSibling;
113-
var names = [];
114-
115-
// Collect text nodes until we hit another heading or structural element
116-
while (contentSibling) {
117-
if (contentSibling.nodeType === Node.ELEMENT_NODE) {
118-
var tag = contentSibling.tagName;
119-
if (tag === 'H2' || tag === 'H3' || tag === 'P' || tag === 'DL') break;
120-
}
101+
// Split by newlines and filter out empty entries
102+
var names = text.split(/[\n\r]+/)
103+
.map(function(s) { return s.trim(); })
104+
.filter(function(s) { return s.length > 0; });
121105

122-
if (contentSibling.nodeType === Node.TEXT_NODE) {
123-
var text = contentSibling.textContent.trim();
124-
if (text) {
125-
// Split by newlines or common separators
126-
var parts = text.split(/[\n\r]+/).map(function(s) { return s.trim(); }).filter(function(s) { return s.length > 0; });
127-
names = names.concat(parts);
128-
}
129-
}
106+
// Only process if we have names
107+
if (names.length === 0) return;
130108

131-
contentSibling = contentSibling.nextSibling;
132-
}
109+
// Clear the div and add wrapped names
110+
div.innerHTML = '';
133111

134-
// If we found names, create a grid container
135-
if (names.length > 1) {
136-
// Create the personnel list container
137-
var container = document.createElement('div');
138-
container.className = 'personnel-list';
139-
140-
// Add each name as a span
141-
names.forEach(function(name) {
142-
var span = document.createElement('span');
143-
span.className = 'personnel-item';
144-
span.textContent = name;
145-
container.appendChild(span);
146-
});
147-
148-
// Remove the old text nodes and insert the new container
149-
var toRemove = [];
150-
contentSibling = sibling.nextSibling;
151-
while (contentSibling) {
152-
if (contentSibling.nodeType === Node.ELEMENT_NODE) {
153-
var tag = contentSibling.tagName;
154-
if (tag === 'H2' || tag === 'H3' || tag === 'P' || tag === 'DL') break;
155-
}
156-
toRemove.push(contentSibling);
157-
contentSibling = contentSibling.nextSibling;
158-
}
159-
160-
// Insert container after h3
161-
sibling.parentNode.insertBefore(container, sibling.nextSibling);
162-
163-
// Remove old nodes
164-
toRemove.forEach(function(node) {
165-
if (node.parentNode) node.parentNode.removeChild(node);
166-
});
167-
}
168-
}
169-
170-
sibling = sibling.nextElementSibling;
171-
}
112+
names.forEach(function(name) {
113+
var span = document.createElement('span');
114+
span.className = 'personnel-item';
115+
span.textContent = name;
116+
div.appendChild(span);
117+
});
118+
});
172119
}
173120

174121
// Convert the static checklist to an interactive form

0 commit comments

Comments
 (0)