function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
ITSS RC 12ITSS RC 12 

How to add Digital Signature to attachment

Hi All,

I have a requiremet to add digital signature to attachments, we have some apps like docu sign,..., but i don't want to use that apps , i want to do some cutomization to achieve this, please any one help on this.

Thanks,
Surya
 
NagendraNagendra (Salesforce Developers) 
Hi ITSS,

Hoping this helps..

I created a custom button on a custom object that launches a Visualforce page to capture the signature of a user. The Visualforce page has two buttons: Capture Signature and Exit. Upon clicking Capture Signature, the canvas is captured and attached in the Notes and Attachments related list of the record. 

Visual Force Page:
<apex:page docType="html-5.0" standardController="EHS_Procedure__c" extensions="ehsSignatureExtensionController">

<script>var $j = jQuery.noConflict();</script>
<apex:stylesheet value="{!URLFOR($Resource.jquerymobile,'/jquerymobile/jquery.mobile-1.3.2.min.css')}"/>
<apex:includeScript value="{!URLFOR($Resource.jquery)}"  />
<apex:includeScript value="{!URLFOR($Resource.jquerymobile,'/jquerymobile/jquery.mobile-1.3.2.min.js')}"/>

<canvas id="signatureCanvas" width="315" height="400" style="border: 1px solid white;"/>  
<apex:includeScript value="/soap/ajax/28.0/connection.js"/>

<script>

sforce.connection.sessionId = "{!$Api.Session_Id}";
var canvas = document.getElementById("signatureCanvas");
var context = canvas.getContext("2d");
var mouseButton = 0;
var lastX = lastY = null;
var ehsId = '{!EHS_Procedure__c.Id}';

function saveSignature() {

    var image = canvas.toDataURL().split(',')[1];
    ehsSignatureExtensionController.saveSignature(ehsId,image,handleResult);
}

function handleResult(result,event) {
    if(result.success) {
        window.top.location.href='/'+ehsId;
    } else {
        alert('Error: '+result.errorMessage);
    }
}

function handleEvent(event) {
    if(event.type==="mousedown"||event.type==="touchstart") {
        mouseButton = event.which || 1;
        lastX = lastY = null;
    }
    if(event.type==="touchcancel" || event.type==="touchcancel" || event.type==="mouseup") {
        mouseButton = 0;
        lastX = lastY = null;
    }
    if((event.type==="touchmove" || event.type==="mousemove") && mouseButton) {
        var newX, newY;
        var canvasX = 0, canvasY = 0, obj = event.srcElement || event.target;
        do {
            canvasX += obj.offsetLeft;
            canvasY += obj.offsetTop;
        } while(obj = obj.offsetParent);
        if(event.targetTouches && event.targetTouches.length) {
            newX = event.targetTouches[0].clientX - (canvasX/2);
            newY = event.targetTouches[0].clientY - (canvasY/2);
        } else {
            newX = event.offsetX;
            newY = event.offsetY;
        }
        if(!lastX && !lastY) {
            lastX = newX;
            lastY = newY;
            context.beginPath();
            context.moveTo(lastX,lastY);
            context.lineTo(lastX,lastY,lastX,lastY);
            context.stroke();
        } else {
            context.beginPath();
            context.moveTo(lastX,lastY);
            context.lineTo(newX,newY);
            context.stroke();
            lastX = newX;
            lastY = newY;
        }
    }
    if(event.type=="touchmove" || event.type==="mousedrag" || (event.type==="selectstart" && (event.srcElement||event.target)===canvas)) {
        event.returnValue=false;
        event.stopPropagation();
        event.preventDefault();
        return false;
    }
}

canvas.addEventListener("mousedrag",handleEvent,true);
canvas.addEventListener("mousemove",handleEvent,true);
canvas.addEventListener("mousedown",handleEvent,true);
window.addEventListener("mouseup",handleEvent,true);
canvas.addEventListener("touchstart",handleEvent,true);
canvas.addEventListener("touchmove",handleEvent,true);
window.addEventListener("touchend",handleEvent,true);
window.addEventListener("selectstart",handleEvent,true);

</script>

<apex:form >
    <button onclick="saveSignature()">Capture Signature</button>
    <apex:commandButton action="{!cancel}" value="Exit"/>
</apex:form>

</apex:page>
Apex Controller:
public with sharing class ehsSignatureExtensionController {

private final EHS_Procedure__c ehs;

public ehsSignatureExtensionController(ApexPages.StandardController controller) {
    ehs = (EHS_Procedure__c)controller.getRecord();
}

@RemoteAction public static RemoteSaveResult saveSignature(Id ehsId, String signatureBody) {
    Attachment a = new Attachment(ParentId=ehsId, name='Signature.png', ContentType='image/png', Body=EncodingUtil.base64Decode(signatureBody));
    Database.saveResult result = Database.insert(a,false);
    RemoteSaveResult newResult = new RemoteSaveResult();
    newResult.success = result.isSuccess();
    newResult.attachmentId = a.Id;
    newResult.errorMessage = result.isSuccess()?'':result.getErrors()[0].getMessage();
    return newResult;
}

public class RemoteSaveResult {
    public Boolean success;
    public Id attachmentId;
    public String errorMessage;
}

public pageReference cancel(){
    pageReference page = new PageReference('/'+ehs.id);
    page.setRedirect(true);
    return page;
}
}
For more information please check with the below threads.
  • https://corycowgill.blogspot.sg/2013/12/capturing-signatures-with-html5-canvas.html
  • http://teach-force.blogspot.sg/2014/02/capture-signature-on-ipad-using.html
Please let us know if this helps you or do you need something else.

Best Regards,
Nagendra.P

 
Dushyant SonwarDushyant Sonwar
I think this is what you are looking for..
http://ibirdstechshare.blogspot.in/2015/09/salesforce-visualforce-signature-tool.html
Hope this helps..
Bashar FatohiBashar Fatohi
Hi Nagendra 
Your code is working perfectly on desktop version. I tried different to make it work on mobile devices but unfortunately, I could not.  Please advise if there any changes I need to make.
Thank you  
Chethan SNChethan SN
Hi Bashar,
Were you able to resolve that issue? If Yes can you please let me know how did you do that ?
Irfan Khan 56Irfan Khan 56
Hi cheethan can you please help me to implent the esignature in lightining?
 
Sai Krishna GurijalaSai Krishna Gurijala
Hi All,

I have a requiremet to add digital signature to attachments, we have some apps like docu sign,..., but i don't want to use that apps , i want to do some cutomization to achieve this, please any one help on this.

Did anyone implemeted this? please help me thanks in advance

Sai
Ellie DivaEllie Diva
Are you searching for an effective antivirus software product for your computer systems and mobile devices? Unable to decide which antivirus software program you should choose to secure your devices? Nowadays, with the increasing cases of cyber threats, using antivirus software has become necessary. No one of us wants to face any chances of cyber threats. And to avoid that, you should use the best antivirus software program on your devices. If you are searching for one, then you should definitely check out the Webroot.com/safe (https://web8root.com) SecureAnyWhere website once.
Peter Jones 20Peter Jones 20
The downloading procedure is pretty easy for the existing users, but it could be a little mind-boggling for the new user. If you are new to McAfee.com/activate (https://activatem9.co.uk) security, you can follow these steps to make your downloading procedure simple and easy.