Migrer de Quick PDF Library et PdfiumViewer vers sgcPDF

Foxit a mis fin à Quick PDF Library le 13 décembre 2021, et le dépôt PdfiumViewer est en lecture seule depuis le 2 août 2019. sgcPDF remplace les deux : du Pascal pur compilé dans votre exe Delphi, et du C# managé pour WinForms, sans DLL PDF à déployer. Ce kit fait correspondre les fonctions de Quick PDF Library et les classes de PdfiumViewer à sgcPDF, avec du code issu de deux exemples qui compilent et réussissent leur autotest.

Des applications bâties sur une bibliothèque PDF qui n'évolue plus

Deux cas courants : une application Delphi qui crée, fusionne, remplit et affiche des fichiers PDF avec Quick PDF Library, et une application WinForms qui affiche des fichiers PDF avec PdfiumViewer.

Depuis Quick PDF Library (Delphi)

Quick PDF Library (Debenu Quick PDF Library, puis Foxit Quick PDF Library) est livrée sous forme de DLL, d'ActiveX ou de LIB avec une clé de déverrouillage, et travaille sur un seul objet dont un document, une page, une police et une image sont "sélectionnés". sgcPDF est un ensemble d'unités Pascal avec un modèle objet : TsgcPDFDocument, TsgcPDFPage, TsgcPDFEditor et TsgcPDFAcroForm, de Delphi 7 à Delphi 13.

Depuis PdfiumViewer (WinForms)

PdfiumViewer encapsule la bibliothèque native PDFium dans un contrôle PdfViewer, un PdfRenderer et un PdfDocument. Il affiche, recherche, rend et imprime les fichiers PDF. sgcPDF les remplace par un seul contrôle managé, TsgcPDFViewerControl, et ajoute ce que PdfiumViewer n'a jamais eu : créer des fichiers PDF, remplir des formulaires, ajouter des annotations et enregistrer les modifications.

Quick PDF Library. L'avis de Foxit (consulté le 20/10/2026) indique en substance : "À partir du 13 décembre 2021, Foxit va mettre fin aux produits suivants", et le premier produit de la liste est Foxit Quick PDF Library (toutes plateformes). Les clients disposant de contrats de maintenance et de support actifs ont été pris en charge jusqu'au 13 décembre 2022 : "Après cette date, le produit passera en fin de support et vous ne serez plus pris en charge." Les remplaçants cités par Foxit sont ses SDK PDF pour Windows, Mac, Linux, Android et iOS, son SDK ActiveX et sa suite de SDK .NET.

PdfiumViewer. Le dépôt GitHub (consulté le 20/10/2026) indique en substance : "Ce dépôt a été archivé par son propriétaire le 2 août 2019. Il est désormais en lecture seule." Son README explique : "Je n'ai pas pu y consacrer de vrai temps depuis longtemps", et "Je ne suis pas en mesure d'assurer correctement le support de ce projet." Il précise aussi : "Le contrôle PdfiumViewer nécessite les bibliothèques natives PDFium. Elles ne sont pas incluses dans le paquet NuGet de PdfiumViewer." Le paquet NuGet a été mis à jour pour la dernière fois le 06/11/2017 (version 2.13.0) et cible net20.

Une seule bibliothèque PDF, code source inclus

sgcPDF est le produit PDF de sgcUI. Il crée, modifie, remplit, signe, chiffre, rend et affiche des fichiers PDF en Delphi et en .NET.

Aucune DLL PDF à livrer

En Delphi, les unités sgcPDF sont compilées dans l'exe : pas de DLL, d'ActiveX ou de LIB à déployer et à enregistrer, et pas d'appel de clé de déverrouillage. En .NET, sgcPDF est du C# managé, il n'y a donc pas de pdfium.dll ni de paquet natif x86 ou x64 à choisir : l'exemple s'exécute en AnyCPU.

Un modèle objet

Chaque appel reçoit l'objet page ou l'index, l'état "sélectionné" de Quick PDF Library disparaît donc. L'imposition utilise des XObjects de formulaire vectoriels (AddPageAsForm, DrawForm, DrawFormInRect), les formulaires utilisent AcroForm, et le chiffrement va jusqu'à AES-256 (emAES_256).

Une visionneuse qui modifie

TsgcPDFViewerControl ajuste l'affichage à la largeur, à la page ou à la hauteur, fait pivoter la vue, recherche et imprime avec une boîte de dialogue, et en .NET il fournit un PrintDocument comme PdfiumViewer. Il remplit aussi les champs de formulaire (FormFilling), ajoute des annotations à la souris (AnnotationTool) et sélectionne du texte. Vues latérales : TsgcPDFThumbnailView, TsgcPDFOutlineView, TsgcPDFCommentsView.

sgcPDF est vendu séparément, à partir de €249 pour un seul développeur en Delphi et C++ Builder et à partir de €249 pour .NET, avec le code source complet et 1 an de mises à jour, et il fait partie de sgcUI Enterprise et du bundle All-Access. Les paquets .NET existent aussi en paquets Community gratuits sur NuGet, esegece.sgcPDF.Community et esegece.sgcPDF.WinForms.Community, avec les mêmes fonctions. Voir la page produit sgcPDF.

Les fonctions de Quick PDF Library dans sgcPDF

Les unités sont sgcPDF_Types, sgcPDF_Fonts et sgcPDF_Document, plus sgcPDF_Editor, sgcPDF_Encryption, sgcPDF_Renderer_GDI et sgcPDF_Export si nécessaire. Les index de page de sgcPDF commencent à 0.

Quick PDF Library sgcPDF
UnlockKeyrien à appeler dans le code
NewDocumentTsgcPDFDocument.Create, puis AddPage (un nouveau document n'a aucune page tant que vous n'en ajoutez pas)
NewPage, SetPageDimensions, SetPageSizeTsgcPDFDocument.AddPage(AWidth, AHeight): TsgcPDFPage, InsertPage(AIndex, AWidth, AHeight)
LoadFromFile, LoadFromStringTsgcPDFDocument.LoadFromFile, LoadFromStream, LoadFromBytes
LoadFromFile avec un mot de passeTsgcPDFDocument.SetPassword(APassword) avant LoadFromFile
SaveToFile, SaveToStringTsgcPDFDocument.SaveToFile, SaveToStream, SaveIncremental
PageCountTsgcPDFDocument.PageCount; pour un fichier uniquement, sgcPDFGetPageCount(AFileName)
SelectPageTsgcPDFDocument.Pages[AIndex] (base 0, propriété par défaut), GetPage(AIndex)
SetInformationTsgcPDFDocument.Info.Title, .Author, .Subject, .Keywords, .Creator, .Producer
AddStandardFont + SelectFont + SetTextSize + DrawTextTsgcPDFPage.DrawText(AText, X, Y, AFont, AFontSize) avec un TsgcPDFStandardFont (sfHelvetica, sfTimesRoman, sfCourier et leurs variantes gras et italique)
SetTextColor + DrawTextTsgcPDFPage.DrawTextColor(AText, X, Y, AFont, AFontSize, R, G, B) (composantes de 0 à 1)
AddTrueTypeFont + DrawTextTsgcPDFDocument.AddTrueTypeFont(AFontName, ABold, AItalic): Integer (ou AddTrueTypeFontFromFile), puis TsgcPDFPage.DrawTextTT
DrawLine, DrawBoxTsgcPDFPage.DrawLine(X1, Y1, X2, Y2, ALineWidth), DrawRectangle(X, Y, W, H, ALineWidth), DrawRectangleFill
AddImageFromFile + SelectImage + DrawImageTsgcPDFDocument.AddImage(AFileName): Integer + TsgcPDFPage.DrawImageFromIndex(AIndex, X, Y, W, H), ou DrawImageFile(AFileName, X, Y, W, H)
GetPageTextTsgcPDFDocument.ExtractTextW(APageIndex), ExtractText, FindText; TsgcPDFEditor.ExtractAllText, SearchText
AddToFileList + MergeFileListsgcPDFMergeFiles([...], AOutputFile)
MergeDocumentTsgcPDFDocument.AppendDocument(ADoc), TsgcPDFEditor.MergeFrom(AFileName)
ExtractPageRanges, ExtractFilePagessgcPDFExtractPages(AInputFile, AOutputFile, ARange) (chaîne de plages en base 1, comme '1,3,5-9'), TsgcPDFEditor.ExtractPages(ARange, AOutputFileName)
DeletePagesTsgcPDFDocument.DeletePages(ARange), DeletePage(AIndex)
RotatePageTsgcPDFEditor.RotatePage(AIndex, ADegrees)
SetTransparency + DrawText (filigrane)TsgcPDFEditor.AddWatermarkAllPages(TsgcPDFWatermarkOptions), AddWatermark, AddTransparentText
DrawText sur chaque page (tampon, en-tête, pied de page)TsgcPDFEditor.AddTextColor, AddHeaderText, AddFooterText, AddPageNumbers
RenderPageToDCTsgcPDFRendererGDI.RenderPage(ADC, ADocument.Parser, APage.PageDict, AWidth, AHeight); dans la visionneuse VCL TsgcPDFViewerControl.RenderPageToBitmap
RenderPageToFileTsgcPDFExporter.ExportPage(ADocument, APageIndex, AFileName) (BMP, PNG, JPEG), sgcPDFPageToImage(APDFFile, AImageFile, APageIndex, ADPI)
FormFieldCount, FindFormFieldByTitleTsgcPDFDocument.AcroForm.FieldCount, AcroForm.FindField(AName)
SetFormFieldValue, SetFormFieldValueByTitleAcroForm.FillField(AName, AValue), AcroForm.SetCheckBox(AName, AChecked), TsgcPDFEditor.FillFormField
GetFormFieldValueAcroForm.GetFieldValue(AName)
NewFormFieldAcroForm.AddTextField, AddCheckBox, AddComboBox, AddListBox, AddRadioGroup + AddRadioButton, AddButton, AddSignatureField
FlattenFormFieldAcroForm.FlattenFields, TsgcPDFEditor.FlattenForm
EncryptTsgcPDFDocument.SetEncryption(AMethod, AUserPassword, AOwnerPassword) avec emAES_256, emAES_128, emRC4_128 ou emRC4_40
CapturePageTsgcPDFDocument.AddPageAsForm(ASource, APageIndex): Integer (surcharges avec une zone de page, un rectangle ou des annotations)
DrawCapturedPageTsgcPDFPage.DrawForm(AFormIndex, X, Y, AScaleX, AScaleY, ARotation), DrawFormInRect(AFormIndex, ATarget, AKeepAspect, ARotation), DrawFormMatrix
GetPageBoxTsgcPDFPage.GetPageBox(ABox) (ppbTrimBox, ppbBleedBox, ...), TsgcPDFDocument.GetFormBBox
NewOutlineTsgcPDFEditor.AddBookmark(ATitle, APageIndex), AddBookmarkChild
AddLinkToPageTsgcPDFEditor.AddLinkAnnotation(APageIndex, ALeft, ABottom, ARight, ATop, ADestPage)
AddNoteAnnotationTsgcPDFEditor.AddTextAnnotation(APageIndex, ALeft, ABottom, ARight, ATop, AText)
SignFileTsgcPDFEditor.SignDocument(AOutputFile, ACertSubjectName, AReason, ALocation)
PrintDocumentLa visionneuse VCL TsgcPDFViewerControl.Print(AFromPage, AToPage, ATitle) imprime sans boîte de dialogue, PrintDialog(ATitle) affiche la boîte de dialogue d'impression (plage de pages, copies) et imprime. La visionneuse FireMonkey TsgcPDFViewerFMX a les deux mêmes méthodes sous Windows et macOS.
SetMeasurementUnits(0), SetOrigin(0)le système de coordonnées par défaut et unique : points, origine en bas à gauche ; aides sgcPDFMMToPoints, sgcPDFRectMM

Également dans les visionneuses Delphi : zoom ajusté à la hauteur (zmFitHeight sur TsgcPDFViewerControl, fzmFitHeight sur TsgcPDFViewerFMX, ZoomFitHeight sur TsgcPDFViewer) et rotation de la vue (ViewRotation, RotateLeft, RotateRight), qui fait pivoter la vue et laisse le document inchangé.

Les tâches courantes de Quick PDF Library dans sgcPDF

Chaque extrait est copié de la démo MigrateFromQuickPDF, qui compile avec Delphi 7 (Win32) et Delphi 13 (Win32 et Win64) et réussit son autotest. Les commentaires nomment les appels de Quick PDF Library que chaque ligne remplace.

La clause uses

L'unité d'import de Quick PDF Library et la DLL disparaissent. Ces unités couvrent toutes les tâches de la démo :

frmMain.pas
uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  StdCtrls, ExtCtrls, ShellAPI,
  // sgc
  sgcPDF_Types, sgcPDF_Fonts, sgcPDF_Document, sgcPDF_Encryption,
  sgcPDF_Editor, sgcPDF_Renderer_GDI;

Créer un document avec du texte, un rectangle et une image

Remplace NewDocument, SetInformation, AddStandardFont, SelectFont, SetTextSize, SetTextColor, DrawText, DrawBox, AddImageFromFile, SelectImage, DrawImage et SaveToFile.

frmMain.pas
oDoc := TsgcPDFDocument.Create;
try
  // SetInformation(1, ...) / SetInformation(2, ...)
  oDoc.Info.Title := 'Created with sgcPDF';
  oDoc.Info.Author := 'Migration sample';
  // NewDocument creates page 1, sgcPDF adds every page explicitly
  oPage := oDoc.AddPage(CS_A4_WIDTH, CS_A4_HEIGHT);
  // AddStandardFont(4) + SelectFont + SetTextSize(28) + DrawText
  oPage.DrawText('Hello from sgcPDF', 72, 760, sfHelveticaBold, 28);
  // SetTextColor(r, g, b) + DrawText
  oPage.DrawTextColor('No DLL, pure Pascal.', 72, 725, sfHelvetica, 14,
    0.1, 0.3, 0.7);
  // SetLineColor + SetLineWidth + DrawBox(x, y, w, h, 0)
  oPage.DrawRectangle(72, 520, 260, 120, 1.5);
  // AddImageFromFile + SelectImage + DrawImage(x, y, w, h)
  vImage := oDoc.AddImage(OutFile('logo.bmp'));
  oPage.DrawImageFromIndex(vImage, 102, 540, 200, 80);
  oDoc.SaveToFile(OutFile('created.pdf'));
finally
  oDoc.Free;
end;

Extraire le texte d'une page

Remplace LoadFromFile, PageCount, SelectPage et GetPageText. Notez l'index de page en base 0.

frmMain.pas
oDoc.LoadFromFile(OutFile('input_a.pdf'));
Log('Extract text: input_a.pdf has ' + IntToStr(oDoc.PageCount) +
  ' pages');
// SelectPage(2) + GetPageText(0): sgcPDF page indexes are 0-based
vText := string(oDoc.ExtractTextW(1));
Log(vText);

Fusionner et diviser

Remplace AddToFileList avec MergeFileList, ainsi que ExtractPageRanges ou ExtractFilePages. Les chaînes de plages restent en base 1.

frmMain.pas
sgcPDFMergeFiles([OutFile('input_a.pdf'), OutFile('input_b.pdf')],
  OutFile('merged.pdf'));
frmMain.pas
// 1-based range string, the same syntax as Quick PDF Library
sgcPDFExtractPages(OutFile('merged.pdf'), OutFile('pages_2-3.pdf'), '2-3');
// one file per page: split
sgcPDFExtractPages(OutFile('merged.pdf'), OutFile('page_4.pdf'), '4');

Filigrane et tampon sur chaque page

Remplace SelectPage, SetTransparency, SetTextColor et DrawText dans une boucle sur les pages.

frmMain.pas
oEditor.LoadFromFile(OutFile('input_a.pdf'));
vOptions.Text := 'CONFIDENTIAL';
vOptions.Font := sfHelveticaBold;
vOptions.FontSize := 72;
vOptions.Rotation := 45;
vOptions.Opacity := 0.3;
vOptions.R := 0.8;
vOptions.G := 0.1;
vOptions.B := 0.1;
oEditor.AddWatermarkAllPages(vOptions);
// a stamp in the top right corner of every page
for i := 0 to oEditor.Document.PageCount - 1 do
  oEditor.AddTextColor(i, 'APPROVED', 440, 800, sfHelveticaBold, 16,
    0.0, 0.5, 0.0);
oEditor.SaveToFile(OutFile('watermarked.pdf'));

Rendre une page dans un contexte de périphérique

Remplace RenderPageToDC. Le moteur de rendu prend le Parser du document chargé et le PageDict de la page.

frmMain.pas
oDoc.LoadFromFile(OutFile('created.pdf'));
oPage := oDoc.Pages[0];
// 96 DPI: points are 1/72 inch
vScale := 96 / 72;
vW := Round(oPage.Width * vScale);
vH := Round(oPage.Height * vScale);
oBitmap.PixelFormat := pf24bit;
oBitmap.Width := vW;
oBitmap.Height := vH;
oBitmap.Canvas.Brush.Color := clWhite;
oBitmap.Canvas.FillRect(Rect(0, 0, vW, vH));
oRenderer.RenderPage(oBitmap.Canvas.Handle, oDoc.Parser, oPage.PageDict,
  vW, vH);
GdiFlush;
oBitmap.SaveToFile(OutFile('created_page1.bmp'));

Remplir un formulaire

Remplace FormFieldCount, FindFormFieldByTitle et SetFormFieldValue.

frmMain.pas
oDoc.LoadFromFile(OutFile('form.pdf'));
Log('Fill form: form.pdf has ' + IntToStr(oDoc.AcroForm.FieldCount) +
  ' fields');
oDoc.AcroForm.FillField('Customer', 'ACME Corporation');
oDoc.AcroForm.FillField('Amount', '1250.00');
oDoc.AcroForm.SetCheckBox('Paid', True);
oDoc.SaveToFile(OutFile('form_filled.pdf'));

Chiffrer en AES-256 et ouvrir avec le mot de passe

Remplace Encrypt, ainsi que LoadFromFile avec un mot de passe.

frmMain.pas
oDoc.LoadFromFile(OutFile('input_a.pdf'));
oDoc.SetEncryption(emAES_256, CS_USER_PASSWORD, CS_OWNER_PASSWORD);
oDoc.SaveToFile(OutFile('encrypted.pdf'));
frmMain.pas
oDoc.SetPassword(CS_USER_PASSWORD);
oDoc.LoadFromFile(OutFile('encrypted.pdf'));
vText := string(oDoc.ExtractTextW(0));

Imposition 2-up

Remplace CapturePage, NewPage, SetPageDimensions et DrawCapturedPage. AddPageAsForm conserve chaque page source comme XObject de formulaire, le texte reste donc vectoriel et sélectionnable.

frmMain.pas
oSource.LoadFromFile(OutFile('merged.pdf'));
vHalf := CS_A4_HEIGHT / 2;
oSheet := nil;
for i := 0 to oSource.PageCount - 1 do
begin
  // a landscape A4 sheet for every 2 source pages
  if i mod 2 = 0 then
    oSheet := oTarget.AddPage(CS_A4_HEIGHT, CS_A4_WIDTH);
  // CapturePage
  vForm := oTarget.AddPageAsForm(oSource, i);
  // DrawCapturedPage, scaled to fit the left or the right half
  oSheet.DrawFormInRect(vForm, sgcPDFRect((i mod 2) * vHalf, 0,
    (i mod 2) * vHalf + vHalf, CS_A4_WIDTH), True);
end;
oTarget.SaveToFile(OutFile('imposed_2up.pdf'));

Les classes de PdfiumViewer dans sgcPDF

Espace de noms esegece.sgcPDF, paquet esegece.sgcPDF.WinForms. Les index de page sont en base 0 dans les deux bibliothèques.

PdfiumViewer sgcPDF .NET
PdfViewer (UserControl avec une barre d'outils et un volet de signets)TsgcPDFViewerControl; créez votre propre barre d'outils, signets dans TsgcPDFOutlineView
PdfRenderer (PdfViewer.Renderer)le même TsgcPDFViewerControl
PdfViewer.Document = PdfDocument.Load(path)TsgcPDFViewerControl.LoadFromFile(path) (la visionneuse possède le document), LoadFromStream, ou Document = vDoc (vous le libérez)
PdfDocument.Load(path, password)TsgcPDFDocument.SetPassword avant LoadFromFile, puis TsgcPDFViewerControl.Document = vDoc
PdfDocument.PageCountTsgcPDFViewerControl.PageCount (propriété), TsgcPDFDocument.PageCount() (méthode)
PdfDocument.PageSizesTsgcPDFDocument.GetPage(i).Width et .Height (points)
PdfRenderer.PageTsgcPDFViewerControl.PageIndex, GotoPage, NextPage, PrevPage, FirstPage, LastPage, événement OnPageChange
PdfViewerZoomMode.FitWidthZoomMode = TsgcPDFViewerZoomMode.zmFitWidth
PdfViewerZoomMode.FitHeightTsgcPDFViewerZoomMode.zmFitHeight
PdfViewerZoomMode.FitBestTsgcPDFViewerZoomMode.zmFitPage
Zoom (un facteur, 1.0 = 100 %)TsgcPDFViewerControl.Zoom (un pourcentage, 100 = 100 %, définit zmCustom), ZoomIn, ZoomOut, zmActualSize, ZoomToRect
PdfRenderer.RotateLeft(), RotateRight()TsgcPDFViewerControl.RotateLeft(), RotateRight()
PdfRenderer.RotationTsgcPDFViewerControl.ViewRotation (TsgcPDFViewerRotation: pvr0, pvr90, pvr180, pvr270); PageRotation(i) renvoie la rotation affichée
PdfDocument.Search(text, matchCase, wholeWord) + PdfRenderer.MarkersTsgcPDFViewerControl.FindText(AText, ACaseSensitive, AWholeWord) (surligne et fait défiler), FindNext, FindPrevious, SearchResults, GetSearchMatch(i), ClearSearch
PdfDocument.CreatePrintDocument() + PrintDialog ou PrintPreviewDialogTsgcPDFViewerControl.CreatePrintDocument() renvoie un System.Drawing.Printing.PrintDocument pour les mêmes PrintDialog et PrintPreviewDialog. En un seul appel : PrintDialog(ATitle); sans boîte de dialogue : Print(AFromPage, AToPage, ATitle)
PdfDocument.Render(page, dpiX, dpiY, forPrinting)TsgcPDFViewerControl.RenderPageToBitmap(APageIndex, ref Bitmap, AZoomPercent, ADPI); sans visionneuse sgcPDF_Export.sgcPDFPageToImage or TsgcPDFExporter.ExportPage
PdfDocument.GetPdfText(page)TsgcPDFDocument.ExtractTextW(APageIndex); avec les positions des caractères TsgcPDFViewerControl.PageText(i); sélection à la souris SelectedText, CopyToClipboard
PdfDocument.BookmarksTsgcPDFOutlineView
PdfViewer.LinkClickTsgcPDFViewerControl.OnLinkClick, OpenLinksInBrowser
PdfDocument.Save(path)TsgcPDFDocument.SaveToFile, SaveIncremental(AFileName) (conserve les octets d'origine et ajoute les modifications)
aucun équivalent : remplissage de formulaireTsgcPDFViewerControl.FormFilling = true, OnFieldChange; dans le code AcroForm.FillField, SetCheckBox, GetFieldValue, FindField
aucun équivalent : annotationsTsgcPDFDocument.Annotations.AddText, AddFreeText, AddHighlight, AddStamp, AddLine, AddSquare, AddCircle, puis AnnotationsChanged(); à la souris AnnotationTool et AnnotationEditing
aucun équivalent : créer un PDFTsgcPDFDocument.AddPage, TsgcPDFPage.DrawText, DrawRectangle, AcroForm.AddTextField, AddCheckBox, SaveToFile

Un formulaire PdfiumViewer avec la visionneuse sgcPDF

Chaque extrait est copié de la démo MigrateFromPdfiumViewer, qui compile en Release et réussit son autotest. Les commentaires citent le code PdfiumViewer que chaque bloc remplace.

Un seul contrôle à la place de PdfViewer et PdfRenderer

MainForm.cs
// PdfiumViewer: PdfViewer (UserControl with toolbar) and its PdfRenderer (the page
// surface, PdfViewer.Renderer) -> one control, TsgcPDFViewerControl
private TsgcPDFViewerControl FViewer;
MainForm.cs
FViewer = new TsgcPDFViewerControl();
FViewer.Parent = pnlViewer;
FViewer.Dock = DockStyle.Fill;
// PdfiumViewer: PdfRenderer.DisplayRectangleChanged / polling PdfRenderer.Page -> OnPageChange
FViewer.OnPageChange = DoPageChange;
// PdfiumViewer: none, PdfiumViewer renders form fields but cannot edit them.
// sgcPDF: the user types into text fields and toggles check boxes in the viewer
FViewer.FormFilling = true;
FViewer.OnFieldChange = DoFieldChange;
// PdfiumViewer: none. sgcPDF: AnnotationTool adds notes, highlights, shapes, ink
// and stamps with the mouse; AnnotationEditing moves, resizes and deletes them
FViewer.AnnotationAuthor = "sgcPDF demo";

Ouvrir un fichier

MainForm.cs
// PdfiumViewer: pdfViewer1.Document = PdfDocument.Load(AFileName)
// sgcPDF: the viewer loads and owns the document; to share a document you load
// yourself, assign it: FViewer.Document = vDoc (you dispose it)
FViewer.LoadFromFile(AFileName);
// PdfiumViewer: PdfViewer.ZoomMode = PdfViewerZoomMode.FitWidth
FViewer.ZoomMode = TsgcPDFViewerZoomMode.zmFitWidth;
// PdfiumViewer: PdfDocument.PageCount -> TsgcPDFViewerControl.PageCount
// (or TsgcPDFDocument.PageCount(), a method)
Log("Opened " + Path.GetFileName(AFileName) + ", " + sgcPDF_RTL.IntToStr(FViewer.PageCount) + " pages");

Modes de zoom et rotation de la vue

Ajuster à la largeur, à la page et à la hauteur correspondent un à un. Le zoom est un pourcentage et non un facteur.

MainForm.cs
internal void FitWidth()
{
    // PdfiumViewer: PdfViewerZoomMode.FitWidth -> TsgcPDFViewerZoomMode.zmFitWidth
    FViewer.ZoomMode = TsgcPDFViewerZoomMode.zmFitWidth;
}

internal void FitPage()
{
    // PdfiumViewer: PdfViewerZoomMode.FitBest -> TsgcPDFViewerZoomMode.zmFitPage
    FViewer.ZoomMode = TsgcPDFViewerZoomMode.zmFitPage;
}

internal void FitHeight()
{
    // PdfiumViewer: PdfViewerZoomMode.FitHeight -> TsgcPDFViewerZoomMode.zmFitHeight
    FViewer.ZoomMode = TsgcPDFViewerZoomMode.zmFitHeight;
}

internal void RotateLeft()
{
    // PdfiumViewer: PdfRenderer.RotateLeft() -> TsgcPDFViewerControl.RotateLeft()
    // (ViewRotation turns the view only, the document is not changed)
    FViewer.RotateLeft();
}

internal void RotateRight()
{
    // PdfiumViewer: PdfRenderer.RotateRight() -> TsgcPDFViewerControl.RotateRight()
    FViewer.RotateRight();
}

internal void SetZoomPercent(double APercent)
{
    // PdfiumViewer: PdfRenderer.Zoom is a factor (1.0 = 100%);
    // TsgcPDFViewerControl.Zoom is a percentage (100 = 100%) and sets ZoomMode to zmCustom
    FViewer.Zoom = APercent;
}

Recherche

MainForm.cs
// PdfiumViewer: PdfDocument.Search(text, matchCase, wholeWord) returns PdfMatches
// and the app adds PdfMarker objects to PdfRenderer.Markers to highlight them.
// sgcPDF: FindText highlights every match and scrolls to the first one,
// FindNext / FindPrevious move between them, GetSearchMatch(i) gives page and chars
if (!FViewer.FindText(AText, false, false))
{
    Log("Not found: " + AText);
    return 0;
}
for (int i = 0; i < FViewer.SearchResults; i++)
{
    TsgcPDFViewerSearchMatch vMatch = FViewer.GetSearchMatch(i);
    Log("Match " + sgcPDF_RTL.IntToStr(i + 1) + ": page " + sgcPDF_RTL.IntToStr(vMatch.PageIndex + 1) +
      ", char " + sgcPDF_RTL.IntToStr(vMatch.FirstChar));
}
return FViewer.SearchResults;

Imprimer avec CreatePrintDocument

Le code d'impression de PdfiumViewer garde sa forme : CreatePrintDocument() renvoie un PrintDocument pour un PrintDialog ou un PrintPreviewDialog.

MainForm.cs
// PdfiumViewer: using (PrintDocument d = PdfDocument.CreatePrintDocument())
//   { PrintDialog dlg = new PrintDialog(); dlg.Document = d; if (dlg.ShowDialog() == OK) d.Print(); }
// sgcPDF: TsgcPDFViewerControl.CreatePrintDocument() returns the same kind of
// System.Drawing.Printing.PrintDocument, so the PdfiumViewer code stays as it is. It honours
// the page range (all, some pages, current page), copies and collate of its PrinterSettings.
// A shorter way: FViewer.PrintDialog(title) shows the dialog and prints in one call, and
// FViewer.Print(from, to, title) prints without a dialog (0-based pages, -1 = last page).
if (FViewer.PageCount == 0)
    return;
using (PrintDocument vDoc = FViewer.CreatePrintDocument())
using (PrintDialog vDialog = new PrintDialog())
{
    vDoc.DocumentName = "PdfiumViewer migration sample";
    vDialog.Document = vDoc;
    vDialog.AllowSomePages = true;
    vDialog.AllowCurrentPage = true;
    vDialog.UseEXDialog = true;
    vDoc.PrinterSettings.MinimumPage = 1;
    vDoc.PrinterSettings.MaximumPage = FViewer.PageCount;
    vDoc.PrinterSettings.FromPage = 1;
    vDoc.PrinterSettings.ToPage = FViewer.PageCount;
    if (vDialog.ShowDialog(this) == DialogResult.OK)
        vDoc.Print();
}
MainForm.cs
// PdfiumViewer: PrintPreviewDialog with PdfDocument.CreatePrintDocument()
// sgcPDF: the same with TsgcPDFViewerControl.CreatePrintDocument()
if (FViewer.PageCount == 0)
    return;
using (PrintDocument vDoc = FViewer.CreatePrintDocument())
using (PrintPreviewDialog vPreview = new PrintPreviewDialog())
{
    vPreview.Document = vDoc;
    vPreview.Width = 900;
    vPreview.Height = 700;
    vPreview.ShowDialog(this);
}

Rendre une page dans un bitmap

MainForm.cs
// PdfiumViewer: Image img = PdfDocument.Render(page, dpiX, dpiY, forPrinting)
// sgcPDF: RenderPageToBitmap(page, ref bitmap, zoomPercent, dpi); the bitmap passed
// in is disposed and replaced
Bitmap vBitmap = null;
FViewer.RenderPageToBitmap(APageIndex, ref vBitmap, 100, 150);
try
{
    vBitmap.Save(AFileName, ImageFormat.Png);
    Log("Page " + sgcPDF_RTL.IntToStr(APageIndex + 1) + " rendered at 150 dpi: " +
      sgcPDF_RTL.IntToStr(vBitmap.Width) + " x " + sgcPDF_RTL.IntToStr(vBitmap.Height) + " px, " +
      AFileName);
}
finally
{
    vBitmap.Dispose();
}
// without a viewer (server, batch): one call from file to image
sgcPDF_Export.sgcPDFPageToImage(FViewer.FileName, Path.ChangeExtension(AFileName, null) + "_file.png",
  APageIndex, 72);

Texte de la page

MainForm.cs
// PdfiumViewer: PdfDocument.GetPdfText(page) returns the plain text of a page.
// sgcPDF: TsgcPDFDocument.ExtractTextW(page) is the same plain text, and
// TsgcPDFViewerControl.PageText(page) returns a TsgcPDFTextExtractor with the
// characters and their positions (GetTextWithPositions); the user can also select
// text with the mouse and copy it (SelectedText, CopyToClipboard)
string vText = FViewer.Document.ExtractTextW(APageIndex);
Log("Text of page " + sgcPDF_RTL.IntToStr(APageIndex + 1) + ": " + vText.Trim());
TsgcPDFTextExtractor vExtractor = FViewer.PageText(APageIndex);
if (vExtractor != null)
    Log("Characters with positions: " + sgcPDF_RTL.IntToStr(vExtractor.GetCharCount()));
return vText;

Au-delà de PdfiumViewer : remplir un formulaire et ajouter une note

MainForm.cs
// PdfiumViewer: none (no AcroForm API). sgcPDF: AcroForm.FillField / SetCheckBox,
// then an incremental save keeps the original bytes and appends the change
TsgcPDFDocument vDoc = FViewer.Document;
if (vDoc.AcroForm.FindField("CustomerName") == null)
{
    Log("This document has no CustomerName field, open the generated sample");
    return;
}
vDoc.AcroForm.FillField("CustomerName", "ACME Ltd.");
vDoc.AcroForm.SetCheckBox("Approved", true);
FViewer.ClearCache();
FViewer.Invalidate();
vDoc.SaveIncremental(AFileName);
Log("Form filled and saved: " + AFileName);
MainForm.cs
// PdfiumViewer: none (annotations are only rendered). sgcPDF: the document's
// Annotations manager adds notes, free text, highlights, stamps, lines, shapes and
// ink; the viewer shows them after AnnotationsChanged
TsgcPDFDocument vDoc = FViewer.Document;
int vPage = FViewer.PageIndex;
TsgcPDFTextAnnotation vNote = vDoc.Annotations.AddText(vPage, 420, 760, 444, 784,
  "Migrated from PdfiumViewer to sgcPDF.");
vNote.Author = "sgcPDF demo";
vNote.SetColor(1.0, 0.9, 0.2);
vDoc.Annotations.AddHighlight(vPage, 72, 728, 330, 728, 72, 742, 330, 742);
FViewer.AnnotationsChanged();
vDoc.SaveIncremental(AFileName);
Log("Note and highlight added on page " + sgcPDF_RTL.IntToStr(vPage + 1) + ", saved: " + AFileName);

Pas à pas

Portez une tâche ou un formulaire à la fois, et comparez les fichiers de sortie avant et après.

Delphi : depuis Quick PDF Library

1

Ajouter les unités

Ajoutez le dossier Source de sgcPDF ou le paquet installé, et remplacez l'import de Quick PDF Library par sgcPDF_Types, sgcPDF_Fonts et sgcPDF_Document, plus sgcPDF_Editor, sgcPDF_Encryption et sgcPDF_Renderer_GDI si nécessaire.

2

Supprimer la DLL

Retirez la DLL ou l'ActiveX du déploiement et l'appel UnlockKey du code.

3

Un objet par document

Remplacez l'objet TQuickPDF par un TsgcPDFDocument par document, ou un TsgcPDFEditor pour les tâches de chargement, de modification et d'enregistrement.

4

Les pages sont des objets

Remplacez SelectPage et les appels de dessin par des appels sur le TsgcPDFPage obtenu avec AddPage ou Pages[i], et retirez 1 de chaque numéro de page.

5

Faire correspondre les appels

Utilisez le tableau ci-dessus. Les polices standard sont un argument de DrawText ; les polices TrueType sont ajoutées une fois avec AddTrueTypeFont et dessinées avec DrawTextTT.

6

Imposition

Remplacez CapturePage et DrawCapturedPage par AddPageAsForm et DrawForm ou DrawFormInRect.

7

Comparer la sortie

Exécutez la tâche convertie et vérifiez les fichiers. L'autotest de la démo sert de modèle : il rouvre chaque sortie et vérifie le nombre de pages, le texte et les valeurs du formulaire.

WinForms : depuis PdfiumViewer

1

Retirer les parties natives

Retirez le paquet PdfiumViewer, chaque paquet PdfiumViewer.Native.* et tout pdfium.dll copié à la main, dossiers x86 et x64 compris. Le projet peut revenir en AnyCPU.

2

Ajouter sgcPDF

Ajoutez esegece.sgcPDF.WinForms (ou esegece.sgcPDF.WinForms.Community), qui apporte esegece.sgcPDF, et ajoutez using esegece.sgcPDF;.

3

Remplacer le contrôle

Remplacez le PdfViewer ou le PdfRenderer par un TsgcPDFViewerControl (Dock = Fill) et recréez les boutons de barre d'outils que vous utilisiez sous forme d'appels sur le contrôle.

4

Charger le document

Remplacez PdfDocument.Load et Document = par LoadFromFile, ou chargez vous-même un TsgcPDFDocument et affectez-le à Document.

5

Faire correspondre les membres

Page devient PageIndex ou GotoPage, les modes de zoom correspondent à TsgcPDFViewerZoomMode, le facteur de zoom est multiplié par 100, Search devient FindText, Render devient RenderPageToBitmap.

6

Conserver le code d'impression

Appelez CreatePrintDocument() sur la visionneuse au lieu du document PdfiumViewer ; le code PrintDialog et PrintPreviewDialog reste. Ou utilisez PrintDialog(ATitle).

7

Activer les nouveautés

Facultatif : FormFilling = true, AnnotationTool et SaveIncremental, que PdfiumViewer ne pouvait pas offrir.

Ce qui ne correspond pas un à un

Lisez ceci avant de planifier la migration.

Quick PDF Library

PdfiumViewer

MigrateFromQuickPDF et MigrateFromPdfiumViewer

Les deux démos génèrent leurs propres fichiers d'entrée, aucun PDF externe n'est donc nécessaire, et toutes deux ont un autotest.

Delphi : où la trouver

L'installateur sgcUI la place dans Demos\PDF\Delphi\MigrateFromQuickPDF : sgcPDF_Demo_MigrateFromQuickPDF.dpr, frmMain.pas, frmMain.dfm et un fichier readme.html.

Delphi : comment l'exécuter

Ouvrez le .dpr dans n'importe quel Delphi de 7 à 13 (VCL, Win32 ou Win64), cliquez sur Generate sample inputs, puis sur un bouton quelconque ou sur Run all. La sortie va dans le dossier output à côté de l'exe.

Delphi : autotest

sgcPDF_Demo_MigrateFromQuickPDF.exe /selftest [folder] exécute chaque tâche, vérifie les résultats et écrit selftest.log, qui se termine par SELFTEST OK.

.NET : où la trouver

Dans les démos .NET de sgcUI, dossier PDF\MigrateFromPdfiumViewer de la solution sgcUI_Demos.sln : sgcPDF_Demo_MigrateFromPdfiumViewer.csproj, Program.cs et MainForm.cs.

.NET : comment l'exécuter

dotnet run --project demos\PDF\MigrateFromPdfiumViewer (ajoutez -p:SgcCommunity=true pour l'édition Community), cliquez sur Generate sample, qui écrit et ouvre output\sample.pdf, puis sur un bouton quelconque.

.NET : autotest

sgcPDF_Demo_MigrateFromPdfiumViewer.exe /selftest [folder] ouvre l'exemple, navigue, zoome, ajuste la hauteur, fait pivoter, recherche, rend, compte les pages d'un aperçu avant impression, extrait le texte, remplit le formulaire, ajoute une note et rouvre les fichiers enregistrés. Il écrit selftest.log, qui se termine par SELFTEST OK.

Pour être juste envers les deux bibliothèques : une application bâtie sur Quick PDF Library ou PdfiumViewer continue de fonctionner là où elle est déployée aujourd'hui, et Foxit cite ses propres SDK PDF comme successeurs de Quick PDF Library. sgcPDF est la voie à suivre si vous voulez le code PDF en source Pascal ou C# compilé dans votre application, sans bibliothèque PDF native à livrer, et une seule API qui crée, remplit, annote, signe et chiffre aussi les fichiers que votre visionneuse affiche. Pour les composants et les éditions, voir la page produit sgcPDF.

Meilleur rapport qualité-prix : All-AccessTous les produits eSeGeCe, Support Premium inclus, à partir de €1,059/an.
Voir les tarifs All-Access

Portez dès aujourd'hui votre première tâche PDF

Téléchargez sgcUI avec sgcPDF, ou ajoutez les paquets Community gratuits depuis NuGet, et portez votre première tâche ou votre premier formulaire avec les démos MigrateFromQuickPDF et MigrateFromPdfiumViewer à côté.