diff --git a/CMakeLists.txt b/CMakeLists.txt index 2500489..4fa82c3 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -19,6 +19,8 @@ add_executable(kindle2notes typefactory/convertlatex.h typefactory/convertmarkdown.cpp typefactory/convertmarkdown.h + typefactory/convertorg.cpp + typefactory/convertorg.h typefactory/converter.cpp typefactory/converter.h typefactory/main.cpp diff --git a/README.md b/README.md index fecf9ab..01696b0 100644 --- a/README.md +++ b/README.md @@ -7,6 +7,7 @@ Supported output formats: - LaTeX (`--type=latex`) - Markdown (`--type=md`) +- Org mode (`--type=org`) Highlights are grouped by book title while preserving the order in which books first appear in the input file. @@ -63,6 +64,24 @@ Markdown block quote, followed by an empty notes heading: Empty lines inside highlights are preserved as `>` lines, and Markdown syntax characters are escaped automatically. +### Org mode + +Books and clipping metadata become Org headings. Highlight text is placed in +a quote block followed by an empty notes heading: + +```org +* Book Title + +** - Your Highlight on Location 123-125 | Added on ... + +#+begin_quote +Highlighted text line 1 +Highlighted text line 2 +#+end_quote + +*** Notes +``` + ## Architecture Input parsing is implemented as a stage-driven pipeline with one handler for @@ -112,6 +131,15 @@ Generate Markdown: --type=md ``` +Generate Org mode: + +```bash +./build/kindle2notes \ + --input "My Clippings.txt" \ + --output notes.org \ + --type=org +``` + Short options are also available: ```bash @@ -122,7 +150,7 @@ Short options are also available: | --- | --- | --- | | `--input` | `-i` | Path to the Kindle clippings file | | `--output` | `-o` | Path to the generated file | -| `--type` | `-t` | Output format: `latex` or `md` | +| `--type` | `-t` | Output format: `latex`, `md`, or `org` | | `--help` | `-h` | Show usage information | If an unsupported output type is requested, the program prints the list of diff --git a/typefactory/convertorg.cpp b/typefactory/convertorg.cpp new file mode 100644 index 0000000..ade8480 --- /dev/null +++ b/typefactory/convertorg.cpp @@ -0,0 +1,46 @@ +#include "convertorg.h" + +#include +#include +#include +#include + +bool ConverterOrg::save (const std::string &output_file_name) { + if (!parse()) + return false; + + std::ofstream output (output_file_name, std::ios::trunc); + if (!output.is_open()) { + std::cerr << "Failed to open output file: " + << output_file_name + << " (" << std::strerror (errno) << ")\n"; + set_error_code (3); + return false; + } + + const auto &book_titles = titles(); + for (const auto &title : book_titles) { + output << "* " << title << "\n\n"; + + for (std::size_t quote_index = 0; + quote_index < quote_count (title); + ++quote_index) { + output << "** " << quote_meta (title, quote_index) << "\n\n"; + output << "#+begin_quote\n"; + + const auto &text_lines = quote_text_lines (title, quote_index); + std::size_t line_index = 0; + if (!text_lines.empty() && text_lines.front().empty()) + line_index = 1; + + for (; line_index < text_lines.size(); ++line_index) + output << text_lines[line_index] << '\n'; + + output << "#+end_quote\n\n"; + output << "*** Notes\n\n"; + } + } + + set_error_code (0); + return true; +} diff --git a/typefactory/convertorg.h b/typefactory/convertorg.h new file mode 100644 index 0000000..956a2d0 --- /dev/null +++ b/typefactory/convertorg.h @@ -0,0 +1,13 @@ +#ifndef CONVERTORG_H +#define CONVERTORG_H + +#include "converter.h" + +class ConverterOrg final : public Converter { +public: + using Converter::Converter; + + bool save (const std::string &output_file_name) override; +}; + +#endif // CONVERTORG_H diff --git a/typefactory/kindle2notes.pro b/typefactory/kindle2notes.pro index 51323a7..5da7b81 100644 --- a/typefactory/kindle2notes.pro +++ b/typefactory/kindle2notes.pro @@ -7,11 +7,13 @@ CONFIG -= qt SOURCES += \ convertlatex.cpp \ convertmarkdown.cpp \ + convertorg.cpp \ converter.cpp \ main.cpp HEADERS += \ convertlatex.h \ convertmarkdown.h \ + convertorg.h \ converter.h \ typefactory.h diff --git a/typefactory/main.cpp b/typefactory/main.cpp index 71b3db6..8eccf67 100644 --- a/typefactory/main.cpp +++ b/typefactory/main.cpp @@ -5,12 +5,13 @@ #include "convertlatex.h" #include "convertmarkdown.h" +#include "convertorg.h" #include "typefactory.h" using ConverterFactory = TypeFactory; -static constexpr std::array kSupportedTypes = { - "latex", "md" +static constexpr std::array kSupportedTypes = { + "latex", "md", "org" }; struct CliArgs { @@ -35,6 +36,7 @@ static ConverterFactory build_converter_factory() { ConverterFactory factory; factory.registerType ("latex"); factory.registerType ("md"); + factory.registerType ("org"); return factory; } diff --git a/typefactory/typefactory.pro b/typefactory/typefactory.pro index 51323a7..5da7b81 100644 --- a/typefactory/typefactory.pro +++ b/typefactory/typefactory.pro @@ -7,11 +7,13 @@ CONFIG -= qt SOURCES += \ convertlatex.cpp \ convertmarkdown.cpp \ + convertorg.cpp \ converter.cpp \ main.cpp HEADERS += \ convertlatex.h \ convertmarkdown.h \ + convertorg.h \ converter.h \ typefactory.h