Book Manuscript Editor

Book Manuscript Editor

Get automated feedback on pacing, word choice, and common writing issues.

Please enter some text to analyze.

'; return; } let fillerCount = 0; let adverbCount = 0; // 1. Analyze filler words for (const word in fillerWords) { const regex = new RegExp(`\\b${word}\\b`, 'gi'); const matches = text.match(regex); if (matches) { fillerCount += matches.length; text = text.replace(regex, `${word}`); } } // 2. Analyze adverbs (-ly words) const adverbRegex = /\b(\w+ly)\b/gi; const adverbMatches = text.match(adverbRegex); if (adverbMatches) { adverbCount = adverbMatches.length; text = text.replace(adverbRegex, (match) => `${match}`); } // 3. Analyze dialogue tags const dialogueRegex = /(["'])said\b/gi; text = text.replace(dialogueRegex, (match) => `${match}`); analysisOutput.innerHTML = text; // 4. Calculate metrics const words = textInput.value.trim().split(/\s+/); const wordCount = words.length; const sentences = textInput.value.match(/[^.?!]+[.?!]+(\s|$)/g) || []; const sentenceCount = sentences.length || 1; // Simple syllable counter (heuristic) const countSyllables = (word) => { word = word.toLowerCase(); if(word.length <= 3) return 1; word = word.replace(/(?:[^laeiouy]es|ed|[^laeiouy]e)$/, ''); word = word.replace(/^y/, ''); const matches = word.match(/[aeiouy]{1,2}/g); return matches ? matches.length : 0; }; const totalSyllables = words.map(countSyllables).reduce((a, b) => a + b, 0); // Flesch-Kincaid Readability Score const readability = 206.835 - 1.015 * (wordCount / sentenceCount) - 84.6 * (totalSyllables / wordCount); // Update UI readabilityScoreEl.textContent = Math.max(0, Math.round(readability)); fillerWordsCountEl.textContent = fillerCount; adverbsCountEl.textContent = adverbCount; wordCountEl.textContent = wordCount; outputSection.classList.remove('hidden'); }; const downloadPdf = () => { const { jsPDF } = window.jspdf; const doc = new jsPDF({ orientation: 'p', unit: 'mm', format: 'a4' }); const reportTitle = "Manuscript Editorial Report"; const genDate = new Date().toLocaleDateString('en-US'); const pageWidth = doc.internal.pageSize.getWidth(); const margin = 15; let yPos = 0; // --- PDF Template --- doc.setFillColor(22, 101, 52); // green-800 doc.rect(0, 0, pageWidth, 28, 'F'); doc.setFont('helvetica', 'bold'); doc.setFontSize(16); doc.setTextColor(255, 255, 255); doc.text(reportTitle, margin, 18); yPos = 40; // Summary Section doc.setFont('helvetica', 'bold'); doc.setFontSize(12); doc.setTextColor(30, 41, 59); doc.text("Editorial Summary", margin, yPos); yPos += 8; doc.autoTable({ startY: yPos, head: [['Metric', 'Result', 'Notes']], body: [ ['Readability Score', readabilityScoreEl.textContent, 'Score out of 100. Higher is easier to read.'], ['Filler Words Found', fillerWordsCountEl.textContent, 'Words that often weaken writing.'], ['Adverbs (-ly) Found', adverbsCountEl.textContent, 'Consider replacing with stronger verbs.'], ['Total Word Count', wordCountEl.textContent, ''], ], theme: 'grid', headStyles: { fillColor: [21, 128, 61] }, // green-700 margin: { left: margin, right: margin } }); yPos = doc.autoTable.previous.finalY + 15; // Annotated Manuscript doc.setFont('helvetica', 'bold'); doc.setFontSize(12); doc.setTextColor(30, 41, 59); doc.text("Annotated Manuscript", margin, yPos); yPos += 8; html2canvas(analysisOutput, { scale: 2, useCORS: true }).then(canvas => { const imgData = canvas.toDataURL('image/png'); const imgProps = doc.getImageProperties(imgData); const pdfWidth = pageWidth - (margin * 2); const pdfHeight = (imgProps.height * pdfWidth) / imgProps.width; if (yPos + pdfHeight > 280) { doc.addPage(); yPos = 20; } doc.addImage(imgData, 'PNG', margin, yPos, pdfWidth, pdfHeight); // Footer const pageCount = doc.internal.getNumberOfPages(); for(let i = 1; i <= pageCount; i++) { doc.setPage(i); const footerY = doc.internal.pageSize.getHeight() - 15; doc.setLineWidth(0.2); doc.setDrawColor(134, 239, 172); // green-300 doc.line(margin, footerY, pageWidth - margin, footerY); doc.setFontSize(8); doc.setTextColor(100, 116, 139); doc.text(`Report Generated on: ${genDate}`, margin, footerY + 8); doc.text(`Page ${i} of ${pageCount}`, pageWidth - margin, footerY + 8, { align: 'right' }); } doc.save(`Manuscript_Editorial_Report.pdf`); }).catch(err => { console.error("Error generating PDF:", err); alert("Could not generate PDF. See console for details."); }); }; // --- Event Listeners --- analyzeBtn.addEventListener('click', analyzeManuscript); downloadPdfBtn.addEventListener('click', downloadPdf); });
Scroll to Top