Go to the "Question Builder" tab to start adding your survey questions.
';
return;
}
// Group questions by category
const categorizedQuestions = questions.reduce((acc, q) => {
acc[q.category] = acc[q.category] || [];
acc[q.category].push(q);
return acc;
}, {});
let questionCounter = 1;
for (const category in categorizedQuestions) {
const categoryDiv = document.createElement('div');
categoryDiv.className = 'draft-category';
categoryDiv.innerHTML = `
${category}
`;
categorizedQuestions[category].forEach(q => {
const questionDiv = document.createElement('div');
questionDiv.className = 'draft-question';
questionDiv.innerHTML = `
${questionCounter++}. ${q.text}
${responseTypeMap[q.type].display}
${getFormattedOptions(q)}
`;
categoryDiv.appendChild(questionDiv);
});
surveyDraftArea.appendChild(categoryDiv);
}
}
function renderQuestionConfigTable() {
questionTableBody.innerHTML = '';
questions.forEach(q => {
const row = document.createElement('tr');
row.innerHTML = `
${q.category} |
${q.text.substring(0, 50)}... |
${responseTypeMap[q.type].display} |
|
`;
questionTableBody.appendChild(row);
});
// Re-render draft whenever the config changes
renderSurveyDraft();
}
// --- Config Management Functions ---
function updateOptionsVisibility() {
const type = questionTypeSelect.value;
const needsOptions = responseTypeMap[type]?.options;
optionsGroup.style.display = needsOptions ? 'flex' : 'none';
// Populate default options if necessary and options are shown
if (type === 'likert' && needsOptions) {
if (questionOptionsTextarea.value.trim() === '') {
questionOptionsTextarea.value = responseTypeMap['likert'].defaultOptions.join('\n');
}
} else if (type === 'binary' && needsOptions) {
if (questionOptionsTextarea.value.trim() === '') {
questionOptionsTextarea.value = responseTypeMap['binary'].defaultOptions.join('\n');
}
}
}
function resetQuestionForm() {
questionForm.reset();
questionIdToEditInput.value = '';
questionSaveBtn.textContent = 'Add Question';
questionSaveBtn.style.backgroundColor = 'var(--success-color)';
questionCategorySelect.value = 'Health Behavior';
questionTypeSelect.value = 'multiple_choice_single';
updateOptionsVisibility();
}
window.editQuestion = (id) => {
const q = questions.find(item => item.id === id);
if (q) {
questionIdToEditInput.value = q.id;
questionTextInput.value = q.text;
questionCategorySelect.value = q.category;
questionTypeSelect.value = q.type;
questionOptionsTextarea.value = q.options.join('\n');
updateOptionsVisibility();
questionSaveBtn.textContent = 'Update Question';
questionSaveBtn.style.backgroundColor = 'var(--primary-color)';
questionForm.scrollIntoView({ behavior: 'smooth', block: 'start' });
}
};
function handleSaveQuestion(e) {
e.preventDefault();
const type = questionTypeSelect.value;
const needsOptions = responseTypeMap[type]?.options;
const questionData = {
id: questionIdToEditInput.value || `q_${Date.now()}`,
text: questionTextInput.value,
category: questionCategorySelect.value,
type: type,
options: needsOptions ? questionOptionsTextarea.value.split('\n').map(opt => opt.trim()).filter(opt => opt !== '') : []
};
if (questionIdToEditInput.value) {
// Update existing
const index = questions.findIndex(s => s.id === questionIdToEditInput.value);
if (index !== -1) {
questions[index] = questionData;
}
} else {
// Add new
questions.push(questionData);
}
renderQuestionConfigTable();
resetQuestionForm();
}
window.deleteQuestion = (id) => {
if (confirm('Are you sure you want to delete this question?')) {
questions = questions.filter(q => q.id !== id);
renderQuestionConfigTable();
if (questionIdToEditInput.value === id) {
resetQuestionForm();
}
}
};
// --- PDF Functions ---
function downloadPDF() {
const { jsPDF } = window.jspdf;
const doc = new jsPDF('p', 'pt', 'a4');
const finalY = 40;
let currentY = finalY;
const margin = 30;
doc.setFontSize(20);
doc.text("Public Health Survey Draft", margin, currentY);
currentY += 10;
doc.setFontSize(10);
doc.text("Formatted for Data Collection Standardization", margin, currentY);
currentY += 20;
const checkPageBreak = (spaceNeeded) => {
if (currentY + spaceNeeded > doc.internal.pageSize.height - margin) {
doc.addPage();
currentY = margin;
}
};
const categorizedQuestions = questions.reduce((acc, q) => {
acc[q.category] = acc[q.category] || [];
acc[q.category].push(q);
return acc;
}, {});
let questionCounter = 1;
doc.setFont('helvetica', 'normal');
for (const category in categorizedQuestions) {
checkPageBreak(25);
doc.setFontSize(14);
doc.setFont('helvetica', 'bold');
doc.setTextColor(0, 123, 255); // Primary color
doc.text(category.toUpperCase(), margin, currentY);
doc.setLineWidth(0.5);
doc.setDrawColor(0, 123, 255);
doc.line(margin, currentY + 3, doc.internal.pageSize.width - margin, currentY + 3);
currentY += 15;
doc.setTextColor(51, 51, 51); // Font color
categorizedQuestions[category].forEach(q => {
const questionText = `${questionCounter++}. ${q.text}`;
const typeText = `[Type: ${responseTypeMap[q.type].display}]`;
const optionsText = `Options: ${getFormattedOptions(q)}`;
// Question Text
checkPageBreak(30);
doc.setFontSize(11);
doc.setFont('helvetica', 'bold');
let lines = doc.splitTextToSize(questionText, doc.internal.pageSize.width - margin * 2 - 10);
doc.text(lines, margin + 5, currentY);
currentY += (lines.length * 10) + 2;
// Type and Options
doc.setFontSize(10);
doc.setFont('helvetica', 'italic');
doc.setTextColor(100, 100, 100);
lines = doc.splitTextToSize(typeText, doc.internal.pageSize.width - margin * 2 - 20);
doc.text(lines, margin + 15, currentY);
currentY += (lines.length * 8) + 2;
doc.setFont('helvetica', 'normal');
lines = doc.splitTextToSize(optionsText, doc.internal.pageSize.width - margin * 2 - 20);
doc.text(lines, margin + 15, currentY);
currentY += (lines.length * 8) + 8; // Extra padding after question
doc.setTextColor(51, 51, 51);
});
}
doc.save('public-health-survey-draft.pdf');
}
// --- Tab Navigation ---
function switchTab(tabIndex) {
tabs.forEach((tab, index) => {
tab.classList.toggle('active', index === tabIndex);
contents[index].classList.toggle('active', index === tabIndex);
});
currentTab = tabIndex;
updateNavButtons();
}
function updateNavButtons() {
prevBtn.disabled = currentTab === 0;
nextBtn.disabled = currentTab === tabs.length - 1;
}
tabs.forEach((tab, index) => {
tab.addEventListener('click', () => {
// Re-render draft whenever the config tab is left
if (index === 1) renderQuestionConfigTable();
switchTab(index);
});
});
nextBtn.addEventListener('click', () => {
if (currentTab === 1) renderQuestionConfigTable();
if (currentTab < tabs.length - 1) switchTab(currentTab + 1);
});
prevBtn.addEventListener('click', () => {
if (currentTab > 0) switchTab(currentTab - 1);
});
// --- Event Listeners ---
questionTypeSelect.addEventListener('change', updateOptionsVisibility);
questionForm.addEventListener('submit', handleSaveQuestion);
pdfDownloadBtn.addEventListener('click', downloadPDF);
// --- Initial Setup ---
populateDefaultData();
renderQuestionConfigTable(); // Renders table and initial draft
updateOptionsVisibility();
updateNavButtons();
});