Telerik blogs

The Telerik UI for ASP.NET AJAX RadSignature allows you to add a signature spot to PDFs and includes customization options like brush, stroke and background color. Learn how to add it to your PDF.

In the world of digital signatures, the ability to sign PDF documents is a game changer. And with the RadSignature component from Progress Telerik UI for ASP.NET AJAX, this process has never been easier!

Read on to find out how to effortlessly save a signature within a PDF file using the Telerik Document Processing Libraries (DPL) and to present the signed document in the RadPdfViewer control.

User signs, hits Place button, and the signature appears on a certificate PDF

Whether you’re a developer wanting to integrate a digital signature into your project, or just looking to explore the world of digital signatures, this blog post is the perfect starting point.

Join us as we show you how to:

  • Extract applied signature as PDF
  • Create a new PDF document that includes your signature
  • Load the signed document in a PdfViewer

With the help of Telerik UI for ASP.NET AJAX, we’ll demonstrate how to convert the signature content to PDF and base64 string representation. And the best part—you can preview the PDF file using the built-in RadPdfViewer, and even save the new document with the click of a button. So why wait? Let’s dive into the world of digital signatures and explore the possibilities with RadSignature for ASP.NET AJAX.

Prerequisites

Let’s start with declaring the needed controls on the page:

  1. RadSignature is needed to apply the signature that we want to transfer to the PDF file.

ASPX

<telerik:RadSignature  runat="server"  ID="RadSignature1"  Maximizable="false"  Height="150"  Width="100%"  Rounded="None"></telerik:RadSignature>

Signature is selected

  1. RadPdfViewer is needed to display the PDF file that we are currently working on while exposing some of its useful built-in features such as zoom, download, print, search, toggle selection and paging.

ASPX

<telerik:RadPdfViewer runat="server" ID="RadPdfViewer1" Height="700px">
    <PdfjsProcessingSettings>
        <FileSettings Url="Documents/Document.pdf" />
    </PdfjsProcessingSettings>
</telerik:RadPdfViewer>

PDF viewer

In this sample, we are passing the unsigned PDF file by a relative path through the FileSettings of the PdfViewer. Yet, there are multiple other ways you can populate the Viewer. The most common ones you can find explained in the 5 Different Approaches of Setting up the Content in RadPdfViewer for ASP.NET AJAX blog post.

  1. RadToolBar contains the needed buttons and color pickers which enable the users to customize the Signature appearance and align it to their personal preferences on their own.

ASPX

<telerik:RadToolBar runat="server" ID="RadToolBar1" AutoPostBack="false" OnClientButtonClicked="clientToolBarButtonClicked">
    <Items>
        ...
    </Items>
</telerik:RadToolBar>

Toolbar with brush, stroke, background

The ToolBar is not under the spotlight now, so we will not dig into its details now. It is here just to sweeten the UX of the demo.

  1. RadButton is needed to trigger the whole process prior to signing the document and previewing it.

ASPX

<telerik:RadButton  runat="server"  ID="RadButton1"  Text="Place Your Signature"  Icon-PrimaryIconCssClass="rbSave"  AutoPostBack="false"  Primary="true"  OnClientClicked="processSignature"  />

Place your signature button

Not all heroes wear capes, right? Just like that, not all components are on the front stage—some stay behind the scenes but are still needed:

  1. RadClientExportManager is required to export the applied signature into a PDF format and get its data as a base64 string.

ASPX

<telerik:RadClientExportManager  runat="server"  ID="RadClientExportManager1"  OnClientPdfExporting="clientPdfExporting"></telerik:RadClientExportManager>
  1. RadAjaxManager is there to improve the user experience by performing AJAX requests for passing the signature to the server and the manipulated pdf back to the browser.

ASPX

<telerik:RadAjaxManager ID="RadAjaxManager1" runat="server" OnAjaxRequest="RadAjaxManager1_AjaxRequest" DefaultLoadingPanelID="RadAjaxLoadingPanel1">
    <AjaxSettings>
        <telerik:AjaxSetting AjaxControlID="RadAjaxManager1">
            <UpdatedControls>
                <telerik:AjaxUpdatedControl ControlID="RadPdfViewer1" />
            </UpdatedControls>
        </telerik:AjaxSetting>
    </AjaxSettings>
</telerik:RadAjaxManager>
  1. RadAjaxLoadingPanel is needed to display a progress indicator graphic while processing the data on the server-side.

ASPX

<telerik:RadAjaxLoadingPanel  runat="server"  ID="RadAjaxLoadingPanel1"></telerik:RadAjaxLoadingPanel>

Alongside all the above-mentioned components, we will also need to reference the Telerik Document Processing Libraries (DPL) and specifically the RadPdfProcessing library assemblies necessary for manipulating the content of a PDF file. Find the list of the .dll files required for the RadPdfProcessing in the dedicated documentation page.

Illustration of a computer with RadPDFProcessing

Once we have the components defined, the DPL referenced and the unsigned PDF loaded in the view, we can go ahead with the logic.

I bet you’ve noticed that the event handlers we are going to use are already defined in the control snippets above. So, let’s go through the process after the user has applied their signature and clicks the blue “Place Your Signature” button.

Extract Applied Signature as PDF

The OnClientClicked event of the button fires upon clicking the blue button. In its listener, we can get the canvas element with the applied signature with a bit of jQuery help, and also get the ClientExportManager client-side control. Via the exportToPdf() method of the export manager we can trigger exporting the canvas to a pdf:

JavaScript

processSignature = function (sender, args) {
    //get the ClientExportManager client-side control object
    var clientExportManager = $telerik.findControl(document, "RadClientExportManager1");
    //get the canvas element holding the applied signature
    var signatureElement = $(".k-signature-canvas > canvas");
    //trigger exporting to pdf procedure via the built-in method of the ExportManager
    clientExportManager.exportPDF(signatureElement);
}

After that, the OnClientPdfExporting event of the export manager fires. Here we can get the PDF representation of the signature as a base64string directly from the event arguments (get_dataURI()). Get the AJAX manager and send an AJAX request to the server with the signature data optionally along with a custom file name:

JavaScript

clientPdfExporting = function (sender, args) {
    //get the base64string of the pdf passed for exporting
    var dataRaw = args.get_dataURI();
    //get the RadAjaxManager control object
    var ajaxManager = $telerik.findControl(document, "RadAjaxManager1");
    var fileName = "signature.png";
    //send an ajax request to the server with the signature data and the filename
    ajaxManager.ajaxRequest(fileName + ";" + dataRaw);

    //prevent further execution of the built-in exporting logic of the ExportManager
    args.set_cancel(true);
}

Once the request reaches the server, the AjaxRequest event of the RadAjaxManager fires. There we can get the base64 string of the signature and pass it to the function responsible for generating a signed PDF. Finally, pass the base64 string representation of the signed PDF as content of the PdfViewer.

C#

protected void RadAjaxManager1_AjaxRequest(object sender, Telerik.Web.UI.AjaxRequestEventArgs e)
{
    var base64 = e.Argument.Split(',')[1];

    RadPdfViewer1.PdfjsProcessingSettings.FileSettings.Data = PreparePdf(base64);
}

Create a New PDF Document That Includes Your Signature

Let’s explore the exact purpose of the PreparePdf() method.

With the help of the Document Processing Libraries (DPL), we can easily generate an all-new copy of the unsigned PDF document that we have. Then we can append the signature content we already extracted into the new Pdf document at a desired position.

C#

public string PreparePdf(string pdfData)
{
    byte[] resultingBytes = null;
    byte[] finalBytes = null;

    //initialize a PdfFormatProvider that will be used for processing the pdf conent
    PdfFormatProvider provider = new PdfFormatProvider();

    byte[] renderedBytes = Convert.FromBase64String(pdfData);

    RadFixedDocument document1 = null;
    //generate a RadFixedDocument object holding the signature data
    RadFixedDocument document2 = provider.Import(renderedBytes);

    //import the existing unsigned pdf file in another RadFixedDocument 
    string filePath = Server.MapPath("Documents/Document.pdf");
    using (FileStream input = new FileStream(filePath, FileMode.Open, FileAccess.Read))
    {
        document1 = provider.Import(input);
    }

    //export the unsigned pdf as byte array
    using (MemoryStream ms = new MemoryStream())
    {
        provider.Export(document1, ms);
        resultingBytes = ms.ToArray();
    }

    //pass the byte array of the unsigned pdf and the RadFixedDocument with the applied signature to method that will combine them in a single byte array
    finalBytes = AppendContent(resultingBytes, document2);

    //convert the result to a base64 string and return it so it can be passed as content of the PdfViewer
    string result = Convert.ToBase64String(finalBytes);
    return result;
}

The actual manipulation of the PDF content happens in the AppendContent() method. Its logic heavily relies on the functionalities exposed by the RadPdfProcessing library:

C#

private byte[] AppendContent(byte[] resultingBytes, RadFixedDocument document2)
{
    RadFixedPage foregroundContentOwner = document2.Pages[0];

    MemoryStream ms = new MemoryStream();
    byte[] renderedBytes = null;
    using (MemoryStream stream = new MemoryStream(resultingBytes))
    {
        using (PdfFileSource fileSource = new PdfFileSource(stream))
        {
            using (PdfStreamWriter fileWriter = new PdfStreamWriter(ms, true))
            {
                foreach (PdfPageSource pageSource in fileSource.Pages)
                {
                    using (PdfPageStreamWriter pageWriter = fileWriter.BeginPage(pageSource.Size, pageSource.Rotation))
                    {
                        pageWriter.WriteContent(pageSource);

                        using (pageWriter.SaveContentPosition())
                        {
                            double xCenteringTranslation = (pageSource.Size.Width - foregroundContentOwner.Size.Width) - 320;
                            double yCenteringTranslation = (pageSource.Size.Height - foregroundContentOwner.Size.Height) - 110;
                            pageWriter.ContentPosition.Translate(xCenteringTranslation, yCenteringTranslation);
                            pageWriter.WriteContent(foregroundContentOwner);
                        }
                    }
                }
            }
        }
    }
    renderedBytes = ms.ToArray();
    return renderedBytes;
}

We will not go through each separate class and method of the DPL that is used, but I highly recommend spending some time getting familiar with the RadPdfProcessing Model and Concepts.

Everything written here is live and accessible in this demo. Go on and give it a try right away!

If you like what you see, you can further play with the RadSignature in the online demos or download its absolutely free and fully functional trial and give it a spin.

We value any feedback and the community voice, which you can share at the Feedback Portal too.

Start a Free Trial


Doncho Milkov
About the Author

Doncho Milkov

Doncho Milkov was a Technical Support Officer working with the Progress Telerik UI for ASP.NET AJAX components.

Related Posts

Comments

Comments are disabled in preview mode.