Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<h1 align="center"> Python Beginner-Friendly Projects</h1>

<p align="center">
A curated collection of <b>9 simple yet practical Python projects</b> — perfect for beginners learning loops, functions, logic, and file handling.
A curated collection of <b>10 simple yet practical Python projects</b> — perfect for beginners learning loops, functions, logic, and file handling.
</p>

<p align="center">
Expand Down Expand Up @@ -35,6 +35,8 @@ You'll find small but useful programs — great for understanding **core syntax,
| 7️⃣ | ✅ [To-Do List](To-Do-list/) | Manage daily tasks with add/remove features. |
| 8️⃣ | 🗂️ [File Organizer](file-organizer/) | Automatically sort files into folders by extension. |
| 9️⃣ | 🔢 [Unit Converter](unit-converter/) | Convert between common measurement units. |
| 🔟 | 🔊 [Document to Audio Converter](document-to-audio-converter/) | Convert text from documents (`.docx`) into spoken audio. |


---

Expand Down
89 changes: 89 additions & 0 deletions document-to-audio-converter/Readme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,89 @@
# Document to Audio Converter

A simple Python utility to convert text from Microsoft Word (`.docx`) documents into spoken audio. You can either listen to the audio directly or save it as a `.wav` file.

This script uses a simple, dialog-based interface for file selection and options.

## Features

- Reads text content from `.docx` files.
- Converts the extracted text into speech.
- **Option 1:** Speak the text aloud, paragraph by paragraph.
- **Option 2:** Save the entire text as a single `.wav` audio file.
- Handles missing dependencies and file-opening errors gracefully.

## Requirements

- Python 3.x
- The following Python libraries:
- `pyttsx3`
- `python-docx`
- `pypiwin32` (often required by `pyttsx3` on Windows)

## Installation

1. Clone this repository or download the `Pdftoaudio.py` script.

2. Install the required libraries using pip:

```bash
pip install pyttsx3 python-docx pypiwin32
```

## How to Use

1. Run the script from your terminal:

```bash
python Pdftoaudio.py
```

2. A file dialog will open. Select the `.docx` document you want to convert.

3. A dialog box will ask if you want to save the audio to a file.
- Click **"Yes"** to open a "Save As" dialog and save the output as a `.wav` file.
- Click **"No"** to have the script speak the document's text aloud directly.

4. Follow the on-screen prompts. Status messages will be printed to the console.

## Recent Code Improvements

The script was recently refactored to improve its quality, robustness, and maintainability. Key improvements include:

- **Dependency Management:** Imports are now organized at the top of the file. A startup check was added to ensure the `python-docx` library is installed, providing a user-friendly error message if it's missing.
- **Robustness:**
- The `tkinter` root window is now managed with a `contextmanager`, ensuring it is always properly destroyed.
- A `try...finally` block was added around the text-to-speech engine logic to guarantee that `engine.stop()` is called, preventing the engine from hanging in case of an error.
- **Code Structure & Readability:**
- The `pyttsx3` engine setup was moved into its own helper function (`_initialize_engine`) to keep the main logic clean.
- Type hints and docstrings were added to all functions, making the code self-documenting and easier to understand.

## Future Roadmap

This project is a great starting point, and there are several exciting features planned for the future to make it more powerful and user-friendly.

- **Support for More File Formats:**
- Add support for reading text from **PDF files** (`.pdf`).
- Add support for plain text files (`.txt`).

- **Full Graphical User Interface (GUI):**
- Move away from simple dialog boxes to a complete GUI built with a framework like `tkinter` or `PyQt`.
- The GUI would include features like a progress bar, play/pause/stop controls for live playback, and status displays.

- **Enhanced Audio Controls:**
- Allow the user to select from available system voices.
- Provide a slider or input box to adjust the speech rate and volume directly from the UI.

- **Cross-Platform Compatibility:**
- Test and ensure the script works seamlessly on macOS and Linux. This may involve handling different text-to-speech engine backends.

- **Application Packaging:**
- Package the application as a standalone executable (e.g., using `PyInstaller`) so that users can run it without needing to have Python or any libraries installed.

## Contributing

Contributions are welcome! If you'd like to help with any of the features on the roadmap or fix a bug, please feel free to fork the repository and submit a pull request.

## License

This project is licensed under the MIT License. See the `LICENSE` file for details.
85 changes: 85 additions & 0 deletions document-to-audio-converter/WordtoAudio.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
import pyttsx3
from tkinter import Tk, messagebox
from tkinter.filedialog import askopenfilename, asksaveasfilename
from contextlib import contextmanager

try:
import docx
except ImportError:
# Use a dummy Tk instance for the error message if docx is not installed
root = Tk()
root.withdraw()
messagebox.showerror("Dependency Error", "python-docx library not found.\nPlease install it with: pip install python-docx")
root.destroy()
exit()

@contextmanager
def tkinter_root():
"""Context manager for a withdrawn tkinter root window."""
root = Tk()
root.withdraw()
try:
yield root
finally:
root.destroy()

def _initialize_engine() -> pyttsx3.Engine:
"""Initializes and configures the pyttsx3 engine."""
engine = pyttsx3.init()
rate = engine.getProperty("rate")
engine.setProperty("rate", max(100, rate - 50)) # Slow down a bit more for clarity
engine.setProperty("volume", 1.0)
return engine

def docx_to_audio(docx_path: str):
"""Reads a .docx file and converts its text to audio."""
try:
document = docx.Document(docx_path)
except Exception as e:
messagebox.showerror("Error", f"Failed to open Word document:\n{e}")
return

paragraphs = [p.text for p in document.paragraphs if p.text.strip()]
if not paragraphs:
messagebox.showwarning("No text", "No text found in the Word document.")
return

save_file = messagebox.askyesno("Save audio", "Save audio to a file instead of speaking?")
engine = _initialize_engine()

try:
if save_file:
out_path = asksaveasfilename(title="Save audio as", defaultextension=".wav",
filetypes=[("WAV files", "*.wav"), ("All files", "*.*")])
if not out_path:
messagebox.showinfo("Cancelled", "Save cancelled.")
return
text_to_speak = "\n\n".join(paragraphs)
engine.save_to_file(text_to_speak, out_path)
engine.runAndWait()
messagebox.showinfo("Done", f"Audio saved to:\n{out_path}")
else:
# speak paragraph by paragraph to keep responsiveness
for i, paragraph_text in enumerate(paragraphs, start=1):
if not paragraph_text.strip():
continue
print(f"Speaking paragraph {i}/{len(paragraphs)}...")
engine.say(paragraph_text)
engine.runAndWait()
except Exception as e:
messagebox.showerror("Error", f"Failed during speech processing:\n{e}")
finally:
engine.stop()

def main():
"""Main function to run the docx to audio converter."""
with tkinter_root():
docx_path = askopenfilename(title="Select Word Document", filetypes=[("Word Documents", "*.docx")])
if not docx_path:
print("No file selected. Exiting.")
return

docx_to_audio(docx_path)

if __name__ == "__main__":
main()