Exis.PdfEditor logo

SDK localizar e substituir texto em PDF para .NET

Localizar e substituir texto em arquivos PDF programaticamente com C#. Edição direta de fluxos de conteúdo — sem conversão para DOCX, sem dependências externas, sem perda de dados.

.NET CLI dotnet add package Exis.PdfEditor

PM Console Install-Package Exis.PdfEditor

Por que Exis.PdfEditor

Como outras bibliotecas funcionam

A maioria das bibliotecas PDF .NET — IronPDF, Spire.PDF, Aspose, Syncfusion — substituem texto convertendo o PDF para um formato intermediário, redatando texto e desenhando novo texto por cima, ou reconstruindo páginas do zero.

Esta abordagem danifica:

  • Campos de formulário e caixas de seleção
  • Assinaturas digitais
  • Espaçamento e kerning do texto
  • Layout e posicionamento da página
  • Marcadores e destinos de links

Como o Exis.PdfEditor funciona

O Exis.PdfEditor analisa os fluxos de conteúdo PDF diretamente no nível de bytes. Localiza texto nos operadores PDF reais, modifica apenas os operandos de string selecionados e grava usando atualização incremental de PDF.

Tudo que não é tocado permanece idêntico byte por byte:

  • Campos de formulário e AcroForms: intactos
  • Assinaturas digitais em páginas não modificadas: preservadas
  • Espaçamento e kerning do texto: preservados
  • Layout e estrutura da página: preservados
  • Marcadores, anotações, arquivos incorporados: preservados

Outras bibliotecas

PDF
Converter para formato intermediário
Modificar
Reconverter para PDF
Saída (danificada)

Exis.PdfEditor

PDF
Analisar fluxos de conteúdo
Substituir operandos de texto
Atualização incremental
Saída (idêntica exceto texto substituído)

Code Samples

Substituir texto em um PDF — 3 linhas de código

using Exis.PdfEditor;
using Exis.PdfEditor.Licensing;

ExisLicense.Initialize();  // Free 14-day trial - no key needed

var result = PdfFindReplace.Execute(
    "contract.pdf",
    "contract-updated.pdf",
    "Acme Corporation",
    "Globex Industries");

Console.WriteLine($"Replaced {result.TotalReplacements} occurrences " +
                  $"across {result.PagesModified} pages.");

Múltiplas substituições em uma única passagem

var pairs = new[]
{
    new FindReplacePair("2025", "2026"),
    new FindReplacePair("Draft", "Final"),
    new FindReplacePair("CONFIDENTIAL", "PUBLIC"),
};

var result = PdfFindReplace.Execute(
    "report.pdf",
    "report-final.pdf",
    pairs);

Substituição baseada em padrões com expressões regulares

var options = new PdfFindReplaceOptions { UseRegex = true };

// Replace all US phone numbers with a placeholder
var result = PdfFindReplace.Execute(
    "document.pdf",
    "redacted.pdf",
    @"\(\d{3}\)\s?\d{3}-\d{4}",
    "[PHONE REDACTED]",
    options);

Ativar sua assinatura

// Purchase at officefindreplace.com/Home/pdf-find-replace-csharp - $499/developer/year
ExisLicense.Initialize("XXXX-XXXX-XXXX-XXXX");

// Unlimited pages, no restrictions, no console messages
var result = PdfFindReplace.Execute("large-doc.pdf", "output.pdf", "old", "new");

Text Fitting Options

var options = new PdfFindReplaceOptions
{
    CaseSensitive = true,
    WholeWordOnly = false,
    UseRegex = false,
    UseIncrementalUpdate = true,
    TextFitting = TextFittingMode.Adaptive,  // Best quality text fitting
    MinHorizontalScale = 70,                 // Minimum Tz percentage (50-100)
    MaxFontSizeReduction = 1.5               // Max font size reduction in points
};

var result = PdfFindReplace.Execute(
    "contract.pdf", "updated.pdf",
    "Short Name", "A Much Longer Replacement Name That Needs Fitting",
    options);

Font Color & Highlight

// Color replacement text and add a highlight background
var result = PdfFindReplace.Execute(
    "input.pdf", "output.pdf",
    "old text", "new text",
    new PdfFindReplaceOptions
    {
        ReplacementTextColor = PdfColor.Red,         // Font color of replaced text
        ReplacementHighlightColor = PdfColor.Yellow   // Background highlight behind text
    });

Merge PDFs

// Merge multiple PDFs into one, preserving page dimensions and resources
byte[] merged = PdfMerger.Merge(new[] { "cover.pdf", "report.pdf", "appendix.pdf" });
File.WriteAllBytes("combined.pdf", merged);

// Or write directly to a file
PdfMerger.MergeToFile(new[] { "file1.pdf", "file2.pdf" }, "merged.pdf");

// Merge with page range selection
byte[] selected = PdfMerger.Merge(new[]
{
    new PdfMergeInput(File.ReadAllBytes("doc1.pdf"), new[] { 1, 3, 5 }),
    new PdfMergeInput(File.ReadAllBytes("doc2.pdf"))  // all pages
});

Split PDFs

// Split into individual pages
List<byte[]> pages = PdfSplitter.Split("input.pdf");

// Extract specific pages (1-based)
byte[] subset = PdfSplitter.ExtractPages("input.pdf", new[] { 1, 3, 5 });

// Split to individual files with naming pattern
PdfSplitter.SplitToFiles("input.pdf", "page_{0}.pdf");

Build PDFs from Scratch

byte[] pdf = PdfBuilder.Create()
    .WithMetadata(m => m.Title("Report").Author("Exis"))
    .AddPage(page => page
        .Size(PdfPageSize.A4)
        .AddText("Hello, World!", x: 72, y: 750, fontSize: 24,
            options: o => o.Font("Helvetica").Bold().Color(0, 0, 0.8))
        .AddText("Generated with Exis.PdfEditor", x: 72, y: 720, fontSize: 12)
        .AddLine(72, 710, 523, 710, strokeWidth: 1)
        .AddRectangle(72, 600, 200, 80, fill: true,
            fillRed: 0.95, fillGreen: 0.95, fillBlue: 1.0)
        .AddImage(jpegBytes, x: 300, y: 400, width: 200, height: 150))
    .AddPage(page => page
        .Size(PdfPageSize.Letter)
        .AddText("Page 2", x: 72, y: 700, fontSize: 14))
    .Build();

File.WriteAllBytes("output.pdf", pdf);

Extract Text

// Extract all text from a PDF
PdfTextResult text = PdfTextExtractor.ExtractText("input.pdf");
Console.WriteLine(text.FullText);

// Extract from specific pages only
PdfTextResult partial = PdfTextExtractor.ExtractText("input.pdf", new[] { 1, 3 });

// Structured extraction with position and font data
PdfStructuredTextResult structured = PdfTextExtractor.ExtractStructured("input.pdf");
foreach (var block in structured.Pages[0].TextBlocks)
    Console.WriteLine($"[{block.X:F0},{block.Y:F0}] {block.Text} " +
        $"(font={block.FontName}, size={block.FontSize})");

Inspect Document (No License Required)

PdfDocumentInfo info = PdfInspector.Inspect("input.pdf");

Console.WriteLine($"Pages: {info.PageCount}");
Console.WriteLine($"Title: {info.Title}");
Console.WriteLine($"Fonts: {string.Join(", ", info.FontsUsed)}");
Console.WriteLine($"Encrypted: {info.IsEncrypted}");
Console.WriteLine($"Form fields: {info.FormFieldCount}");

Image Replacement

// Find all images in a PDF
var found = PdfImageEditor.FindImages("input.pdf");
foreach (var img in found.Images)
    Console.WriteLine($"Image #{img.Index}: {img.PixelWidth}x{img.PixelHeight} " +
        $"{img.ColorSpace} {img.Format} on page(s) {string.Join(", ", img.PageNumbers)}");

// Replace all images with a new one
byte[] newLogo = File.ReadAllBytes("new-logo.jpg");
var result = PdfImageEditor.ReplaceAll("input.pdf", "output.pdf", newLogo);
Console.WriteLine($"Replaced {result.ImagesReplaced} of {result.ImagesFound} images");

// Replace specific images by index or page range
var selective = PdfImageEditor.Replace("input.pdf", "output.pdf", newLogo,
    new PdfImageReplaceOptions { ImageIndices = new[] { 0, 2 } });

Auto-Layout Document Builder

byte[] pdf = PdfDocumentBuilder.Create()
    .PageSize(PdfPageSize.A4)
    .Margins(72)
    .WithMetadata(m => m.Title("Report").Author("Exis"))
    .Header(h => h
        .AddText("Quarterly Report", PdfHorizontalAlignment.Center, 12, o => o.Bold())
        .AddLine())
    .Footer(f => f
        .AddLine()
        .AddPageNumber())  // "Page 1 of 3"
    .AddParagraph("Introduction", 18, o => o.Bold())
    .AddSpacing(8)
    .AddParagraph("This report covers Q1 results.")
    .AddSpacing(12)
    .AddTable(t => t
        .Columns(2, 1, 1)
        .AlternatingRowBackground(0.95, 0.95, 1.0)
        .HeaderRow(r => r.AddCell("Product").AddCell("Units").AddCell("Revenue"))
        .AddRow(r => r.AddCell("Widget A").AddCell("1,200").AddCell("$24,000"))
        .AddRow(r => r.AddCell("Widget B").AddCell("850").AddCell("$17,000")))
    .AddPageBreak()
    .AddParagraph("Appendix", 14, o => o.Bold())
    .Build();

Form Filling

// Read form fields
List<PdfFormField> fields = PdfFormFiller.GetFields("form.pdf");
foreach (var field in fields)
    Console.WriteLine($"{field.Name} ({field.FieldType}) = {field.CurrentValue}");

// Fill fields
var result = PdfFormFiller.Fill("form.pdf", "filled.pdf", new Dictionary<string, string>
{
    { "FirstName", "John" },
    { "LastName", "Doe" },
    { "State", "CA" },
    { "AgreeToTerms", "Yes" }  // checkbox
});
Console.WriteLine($"Filled {result.FieldsFilled} fields");

// Flatten form (merge field appearances, remove interactive fields)
PdfFormFiller.Flatten("filled.pdf", "flattened.pdf");

Redaction

var result = PdfRedactor.Redact("input.pdf", "redacted.pdf", new[]
{
    // Text-based redaction
    new PdfRedaction { Text = "CONFIDENTIAL" },

    // Regex pattern (e.g., SSN)
    new PdfRedaction { Text = @"\d{3}-\d{2}-\d{4}", IsRegex = true },

    // Replace with alternative text
    new PdfRedaction { Text = "SECRET", ReplaceWith = "[REDACTED]" },

    // Area-based redaction on specific page
    new PdfRedaction { PageNumber = 3, Area = new PdfRect(100, 200, 300, 50) }
});
Console.WriteLine($"Applied {result.RedactionsApplied} redactions");

Optimization

var result = PdfOptimizer.Optimize("input.pdf", "optimized.pdf", new PdfOptimizeOptions
{
    CompressStreams = true,
    RemoveDuplicateObjects = true,
    RemoveMetadata = false,
    DownsampleImages = true,
    MaxImageDpi = 150
});
Console.WriteLine($"Saved {result.BytesSaved} bytes ({result.ReductionPercent:F1}%)");
Console.WriteLine($"Images downsampled: {result.ImagesDownsampled}");

Digital Signatures (.NET 8, 9, 10+)

using System.Security.Cryptography.X509Certificates;

// Sign a PDF
var cert = new X509Certificate2("certificate.pfx", "password");
PdfSigner.Sign("input.pdf", "signed.pdf", new PdfSignOptions
{
    Certificate = cert,
    Reason = "Approved",
    Location = "New York",
    ContactInfo = "admin@example.com"
});

// Verify a signed PDF
PdfSignatureInfo info = PdfSigner.Verify("signed.pdf");
Console.WriteLine($"Signed: {info.IsSigned}");
Console.WriteLine($"Valid: {info.IsValid}");
Console.WriteLine($"Signer: {info.SignerName}");
Console.WriteLine($"Certificate: {info.CertificateSubject}");
Console.WriteLine($"Issuer: {info.CertificateIssuer}");
Console.WriteLine($"Timestamp: {info.HasTimestamp}");

// Verify all signatures in a multi-signed document
List<PdfSignatureInfo> all = PdfSigner.VerifyAll("multi-signed.pdf");
foreach (var sig in all)
    Console.WriteLine($"{sig.SignerName}: valid={sig.IsValid}");

PDF/A Compliance

// Validate (no license required)
// Levels: PdfA1b, PdfA2b, PdfA2u, PdfA3b, PdfA3u
PdfAValidationResult result = PdfAConverter.Validate("input.pdf", PdfALevel.PdfA2b);
Console.WriteLine($"Compliant: {result.IsCompliant}");
foreach (var v in result.Violations)
    Console.WriteLine($"  [{v.Code}] {v.Message} (auto-fix: {v.CanAutoFix})");

// Convert to PDF/A
byte[] pdfa = PdfAConverter.Convert("input.pdf", PdfALevel.PdfA2b);
File.WriteAllBytes("output-pdfa.pdf", pdfa);

Async API

// All I/O operations have async overloads with CancellationToken support
byte[] merged = await PdfMerger.MergeAsync(inputPaths, cancellationToken);
PdfTextResult text = await PdfTextExtractor.ExtractTextAsync(stream, cancellationToken);
var info = await PdfInspector.InspectAsync(path, cancellationToken);
var result = await PdfOptimizer.OptimizeAsync(data, options, cancellationToken);
var sigs = await PdfSigner.VerifyAllAsync(path, cancellationToken);

// Pattern: ClassName.MethodNameAsync(...) on all classes

Como o Exis.PdfEditor se compara

Recurso Exis.PdfEditor IronPDF Spire.PDF Aspose.PDF Syncfusion
Edição direta de fluxos de conteúdo Renderização HTML Sobreposição de redação Substituição por fragmento Sobreposição de redação
Preserva campos de formulário Parcial Parcial
Preserva assinaturas digitais Páginas não modificadas
Preserva espaçamento/kerning do texto Parcial
Zero dependências nativas .NET puro Motor Chromium
Tamanho da DLL < 500 KB ~250 MB ~20 MB ~40 MB ~15 MB
Substituição em lote multi-par Passagem única Loop manual Loop manual Loop manual Loop manual
.NET Framework 4.8 Apenas .NET 6+
Multiplataforma
Suporte a regex
Preço (por desenvolvedor/ano) $499 $749 $999 $1,175 $995*
Sede 🇺🇸 USA 🇺🇸 USA 🇨🇳 China 🇦🇺 Australia 🇺🇸 USA

Comparação baseada em documentação publicamente disponível de fevereiro de 2026. O suporte a recursos pode variar por versão.
"Edição direta de fluxos de conteúdo" significa que a biblioteca modifica os operadores de texto PDF no local sem converter, re-renderizar ou sobrepor.

Recursos

Edição direta de PDF

Modifica operadores de fluxo de conteúdo. Sem conversão intermediária.

Zero dependências

Sem Ghostscript, sem LibreOffice, sem Chromium. .NET gerenciado puro.

Saída sem perdas

Formulários, assinaturas, anotações, marcadores — tudo preservado.

Multi-alvo

.NET 8, 9, 10+ e .NET Standard 2.0 (.NET Framework 4.6.1+, .NET Core 2.0+, .NET 5-7).

Processamento em lote

Múltiplos pares localizar/substituir executados em uma única passagem.

Expressões regulares

Suporte completo a regex .NET para substituições baseadas em padrões.

Multiplataforma

Windows, Linux, macOS. Onde quer que o .NET funcione.

Pegada pequena

DLL única, menos de 500 KB. Sem binários nativos para implantar.

PDF Merge

Combine multiple PDFs into one document, preserving page dimensions and resources.

PDF Split

Extract individual pages or page ranges into separate PDFs. Split to files with naming patterns.

PDF Builder

Create PDFs from scratch with a fluent API. Add text, images, lines, and rectangles with full formatting control.

Text Extraction

Pull text content from PDF pages. Extract from all pages or specific page ranges.

Document Inspector

Read metadata, fonts, page dimensions, and form field counts. Works without any license.

Image Replacement

Find, analyze, and replace images in PDFs. Swap logos or graphics by index or page range with JPEG/PNG.

Auto-Layout Builder

Create reports with auto-pagination, text wrapping, tables, headers/footers, and page numbers.

Form Filling

Read and fill AcroForm fields including text, checkbox, and dropdown. Lossless form preservation.

Redaction

Text-based, regex pattern, or area-based redaction. Permanently remove sensitive content from PDFs.

Optimization

Compress streams, remove duplicate objects, and reduce file size while preserving document quality.

Digital Signatures

Sign PDFs with X.509 certificates and verify existing signatures. Available on .NET 8, 9, 10+.

PDF/A Compliance

Validate and convert to PDF/A (1b, 2b, 2u, 3b, 3u) for long-term archival. Validation works without a license.

Async API

All I/O operations have async overloads with CancellationToken support for scalable applications.

Preços

Annual Subscription
$499
auto-renews yearly / cancel anytime
  • Páginas ilimitadas
  • Arquivos ilimitados
  • Todos os recursos incluídos
  • Suporte por e-mail
  • Automatic annual renewal

Instale o pacote NuGet e chame ExisLicense.Initialize() — funcionalidade completa por 14 dias. Após o teste, o modo avaliação processa até 3 páginas por documento. Sem marcas d'água. Adquira uma chave de licença em officefindreplace.com/Home/pdf-find-replace-csharp.

Preços em dólares americanos. Uma chave por desenvolvedor. Funciona na máquina de desenvolvimento, servidor de build e produção — sem limites por máquina ou implantação.

Como o teste funciona

Teste (Dias 1–14)

  • Instalar o pacote NuGet
  • Chamar ExisLicense.Initialize()
  • Acesso completo — páginas ilimitadas
  • Sem chave, sem cadastro, sem cartão de crédito

Avaliação (Após o dia 14)

  • O teste expira automaticamente
  • A biblioteca continua funcionando
  • Limitado a 3 páginas por documento
  • Sem marcas d'água na saída
  • Seu código existente continua funcionando

Licenciado

  • Adquirir chave em officefindreplace.com/Home/pdf-find-replace-csharp
  • Chamar ExisLicense.Initialize("sua-chave")
  • Páginas ilimitadas, sem restrições
  • Operação silenciosa — sem mensagens de console

Seu código não muda entre o modo de teste e o modo licenciado. Basta adicionar sua chave quando estiver pronto.

Criado pela Exis LLC

Feito nos EUA — Exis LLC, New Jersey. Desenvolvimento e suporte nos Estados Unidos.
Confiança governamental — O mesmo motor PDF alimenta o Global Office Find Replace Professional, usado por agências federais dos EUA para processamento de documentos.
Mais de 35 anos em software — 8 patentes em processamento de documentos, sensores, criptografia e automação industrial.
Suporte responsivo — Acesso direto por e-mail à equipe de desenvolvimento. Sem fila de tickets.

Perguntas frequentes

Não. O Exis.PdfEditor é uma biblioteca .NET pura sem dependências externas. Não utiliza Office, Acrobat, Ghostscript, LibreOffice, Chromium ou qualquer outra ferramenta externa.
O IronPDF renderiza PDFs via motor Chromium — recria a página, destruindo campos de formulário, espaçamento e assinaturas. O Aspose.PDF usa uma abordagem de substituição de fragmentos de texto que pode deslocar o posicionamento. O Exis.PdfEditor opera diretamente nos operadores de fluxo de conteúdo PDF, preservando tudo exceto o texto selecionado.
Campos de formulário (AcroForms), caixas de seleção, botões de rádio, assinaturas digitais (em páginas não modificadas), anotações, marcadores, arquivos incorporados, hiperlinks e todo o layout e espaçamento. Apenas o texto que você seleciona é modificado.
Sim. A licença por posto de desenvolvedor cobre sua máquina de desenvolvimento, servidor de build e implantação em produção. Sem licenciamento por máquina ou por implantação.
A biblioteca entra em modo avaliação. Continua funcionando mas limita o processamento a 3 páginas por documento. Sem exceções, sem marcas d'água. Seu código existente continua funcionando. Adicione uma chave de licença quando estiver pronto.
Sim. O pacote NuGet inclui um build .NET Standard 2.0 que funciona com .NET Framework 4.6.1 e posterior, incluindo 4.8. Também inclui um build otimizado para .NET 8.
Uma chave de licença por desenvolvedor. A chave fica no seu código fonte. Funciona na sua máquina de desenvolvimento, servidor de build, staging e produção sem limites por máquina. Para equipes, cada desenvolvedor precisa de sua própria chave. Sem fingerprinting de máquina ou servidores de ativação.
Sim. PdfTextExtractor.ExtractText() retorna o conteúdo de texto completo. PdfInspector.Inspect() retorna metadados do documento e contagem de páginas — PdfInspector não requer licença.
O Exis.PdfEditor funciona com PDFs baseados em texto onde o texto está codificado em fluxos de conteúdo. Para documentos digitalizados onde o conteúdo é uma imagem raster, seria necessário executar OCR primeiro para produzir uma camada de texto.
A biblioteca resolve automaticamente as codificações de fontes — ToUnicode CMaps, WinAnsiEncoding, MacRomanEncoding, dicionários de codificação personalizados com /Differences e fontes compostas (CID/Type0) para texto CJK.

Inicie seu teste grátis de 14 dias

dotnet add package Exis.PdfEditor

Iniciar teste grátis Sample App on GitHub

Dúvidas? Envie um e-mail para support@exisone.com — você receberá resposta de um desenvolvedor, não de um bot.