Skip to main content Skip to footer

.NET Developer Guide: How to Convert PDF to a Word Document using C#

Quick Start Guide
Tutorial Concept Learn how to programmatically convert PDF content to a MS Word .docx file utilizing a .NET Word and .NET PDF API library.
What You Will Need
  • Visual Studio 2022 or a later version, or another .NET-compatible editor
  • The .NET SDK (Sample using .NET 8)
Controls Referenced

PDF is an excellent format for distributing documents because it preserves their appearance across devices. That fixed layout becomes less convenient when the content needs to be edited, reused, or moved into another workflow. In those cases, converting the PDF content into a Microsoft Word DOCX file can make the document useful again.

Converting PDF content into an editable Word document requires working with both the source PDF and the destination DOCX format. Utilizing a .NET PDF API and .NET Word API, developers can extract content from the PDF and reconstruct it as an editable Word document.

In this tutorial, we will build a .NET console application that reads a PDF with Document Solutions for PDF .NET, extracts its text and available document structure, and reconstructs that content as an editable DOCX file with Document Solutions for Word .NET. Tagged PDFs allow the application to use semantic structure such as paragraphs and headings, while untagged PDFs can fall back to detected page text.

Get the latest release files for the .NET Word and .NET PDF API libraries today!

How to Convert PDF Content to a Word DOCX File in .NET Apps

  1. Create a .NET Project
  2. Initialize .NET PDF Object & Load Sample PDF
  3. Initialize .NET Word Object
  4. Extract Tagged PDF Paragraphs into the Word Document
  5. Convert an Untagged PDF to a Word Document
  6. Save the .NET Word Document Object as a DOCX File
  7. Add the Command-Line Entry Point

Download a finished sample application.


Create a .NET Project

Create a new console application and enter its directory:

dotnet new console --framework net8.0 --name PdfToWordSample
cd PdfToWordSample

Install the .NET PDF and .NET Word Document Solutions packages:

dotnet add package DS.Documents.Pdf
dotnet add package DS.Documents.Word

Add the namespaces used by the converter to Program.cs:

using GrapeCity.Documents.Pdf;
using GrapeCity.Documents.Pdf.Recognition.Structure;
using GrapeCity.Documents.Word;

GcPdfDocument loads and analyzes the PDF. GcWordDocument represents the DOCX file that the application will create.


Initialize .NET PDF Object & Load Sample PDF

Start with a method that accepts the input and output paths. 

static void PdfToWord(string inputPath, string outputPath)
{
    using var input = File.Open(
        inputPath,
        FileMode.Open,
        FileAccess.Read,
        FileShare.Read);

Initialize the GcPdfDocument, then utilize the Load method passing the input stream.

       var pdfDocument = new GcPdfDocument();
       pdfDocument.Load(input);

Initialize .NET Word Object

Use the GcWordDocument constructor to initialize the .NET Word document object.

       var wordDocument = new GcWordDocument();

Extract Tagged PDF Paragraphs into the Word Document

PDF files can contain a logical structure tree that describes the document's semantic organization. In a tagged PDF, this structure can identify elements such as paragraphs and headings instead of treating the page as only positioned text.

Tagged PDF Example for PDF to Word Docx Conversion Sample App | .NET Developer Tutorial

After loading the PDF and initializing the Word document, first attempt to copy paragraphs from this logical structure:

var paragraphsWritten = TryCopyTaggedParagraphs(pdfDocument, wordDocument);

The TryCopyTaggedParagraphs method retrieves the PDF's logical structure with GetLogicalStructure():

private static int TryCopyTaggedParagraphs(
    GcPdfDocument pdfDocument,
    GcWordDocument wordDocument)
{
    LogicalStructure logicalStructure;
    try
    {
        logicalStructure = pdfDocument.GetLogicalStructure();
    }
    catch
    {
        return 0;
    }
    if (logicalStructure.Elements.Count == 0)
    {
        return 0;
    }

If the PDF does not expose a logical structure, the method returns 0. The converter can then fall back to extracting text from an untagged PDF.

Next, iterate through the structure tree and look for paragraph and heading elements. The sample processes elements whose structure type is P, representing paragraphs, as well as heading elements whose type begins with H. It then calls GetParagraphs() to retrieve the text represented by each structure element.

    var count = 0;
    foreach (var element in DescendantsAndSelf(logicalStructure.Elements))
    {
        var type = element.StructElement.Type;
        if (type != "P" && (string.IsNullOrEmpty(type) || !type.StartsWith('H')))
        {
            continue;
        }
        var textParagraphs = element.GetParagraphs();
        if (textParagraphs is null)
        {
            continue;
        }

For each extracted paragraph, create a corresponding paragraph in the Word document. Rather than adding only plain text, the sample adds each PDF text run into the Word paragraph. It also carries over the run's font size and, when available, its text color.

           foreach (var textParagraph in textParagraphs)
           {
               var paragraph = wordDocument.Body.Paragraphs.Add();
               foreach (var textRun in textParagraph.Runs)
               {
                   var run = paragraph.GetRange().Runs.Add(textRun.GetText());
                   run.Font.Size = textRun.Attrs.FontSize;
                   if (textRun.Attrs.NonstrokeColor.HasValue)
                   {
                       run.Font.Color.RGB = textRun.Attrs.NonstrokeColor.Value;
                   }
               }
               count++;
           }
       }
       return count;
   }

This allows paragraphs and headings to be discovered regardless of how deeply they are nested within the tagged PDF structure.


Convert an Untagged PDF to a Word Document

Not every PDF contains tags or a logical structure tree. For those documents, the application needs another way to reconstruct editable Word content. 

After attempting tagged-PDF extraction, check whether any paragraphs were written:

// Continuation of the PdfToWord method
// Added after the GcWordDocument constructor
        var paragraphsWritten = TryCopyTaggedParagraphs(pdfDocument, wordDocument);
        // Untagged PDFs do not expose a semantic structure tree. In that case,
        // reconstruct editable text from the paragraphs detected on each page.
        if (paragraphsWritten == 0)
        {
            paragraphsWritten = CopyDetectedParagraphs(pdfDocument, wordDocument);
        }
        if (paragraphsWritten == 0)
        {
            throw new InvalidOperationException(
                "No extractable text was found. A scanned PDF requires OCR before conversion.");
        }

If no tagged paragraphs are available, the sample calls CopyDetectedParagraphs

This method utilizes GetTextMap() to iterate through each PDF page and accesses the paragraphs detected by the page's text map.  For every detected paragraph, GetText() retrieves its text and adds it as a new paragraph in the Word document. Empty paragraphs are skipped. 

    private static int CopyDetectedParagraphs(
        GcPdfDocument pdfDocument,
        GcWordDocument wordDocument)
    {
        var count = 0;
        foreach (var page in pdfDocument.Pages)
        {
            foreach (var textParagraph in page.GetTextMap().Paragraphs)
            {
                var text = textParagraph.GetText();
                if (string.IsNullOrWhiteSpace(text))
                {
                    continue;
                }
                wordDocument.Body.Paragraphs.Add(text);
                count++;
            }
        }
        return count;
    }

This fallback is useful for PDFs that contain selectable text but do not include semantic tagging. The result is editable paragraph content in the generated DOCX rather than a page rendered as an image.


Save the .NET Word Document Object as a DOCX File

GcWordDocument.Save writes the reconstructed Word document object as a local DOCX file.

// Continuation of the PdfToWord method
// Added after the paragraphsWritten logic
        wordDocument.Save(outputPath);
        Console.WriteLine(
            $"Reconstructed {paragraphsWritten} paragraph(s) in: {Path.GetFullPath(outputPath)}");
}

Add the Command-Line Entry Point

With the conversion logic complete, add a command-line entry point so the application can accept the source PDF and destination DOCX paths.

The sample defines pdf-to-word as one of its supported commands:

    private const string Usage = """
        PDF to Word Document Solutions conversion sample
        Command:
          pdf-to-word <input.pdf> <output.docx>
        """;

The application's Main method reads the first argument and routes the command to the appropriate conversion method:

case "pdf-to-word" when args.Length == 3:
    PdfToWord(args[1], args[2]);
    break;

Here, args[1] is the input PDF path and args[2] is the output Word document path.

The entry point also handles help output and conversion errors:

public static int Main(string[] args)
{
    try
    {
        if (args.Length == 0 || args[0] is "-h" or "--help")
        {
            Console.WriteLine(Usage);
            return 0;
        }
        // Command handling...
            return 0;
        }
        catch (Exception ex)
        {
            Console.Error.WriteLine($"Conversion failed: {ex.Message}");
            return 1;
        }
    }

This gives the sample a simple command-line interface while returning a nonzero exit code when a conversion fails.

Before performing the conversion, the PdfToWord method also confirms that the source file exists and ensures that the output directory is available:

EnsureInputExists(inputPath);
EnsureOutputDirectory(outputPath);

The corresponding helper methods throw a FileNotFoundException for a missing input file and create the destination directory when necessary.


Run the PDF to Word Converter

You can now run the converter from the project directory:

dotnet run -- pdf-to-word tagged-sample.pdf tagged-output.docx
dotnet run -- pdf-to-word untagged-sample.pdf untagged-output.docx

Run the PDF to Word Conversion .NET Sample Application

The application loads the PDF/s, first attempts to reconstruct its paragraphs from tagged document structure, falls back to page-level paragraph detection for untagged PDFs, and saves the resulting editable content as a Word document.

Extract PDF Content to Add to a Newly Generated DOCX File | .NET C# Tutorial Sample


Conclusion

With Document Solutions for PDF .NET and Document Solutions for Word .NET, you can build a PDF-to-DOCX workflow without Microsoft Word, Adobe Acrobat, or Office interop. Tagged PDFs allow developers to take advantage of their logical document structure, while the text-map fallback provides a way to reconstruct editable paragraphs from untagged PDFs.

From here, you can extend the sample to preserve additional formatting, map PDF headings to Word styles, handle other structure elements, or incorporate OCR into workflows that need to process scanned documents.

Tags:

comments powered by Disqus