Skip to main content

Template Example: Base64 Digital Signatures

This example demonstrates how hand-drawn digital signatures are captured, normalized into black-ink Base64 PNGs, and rendered onto certificates.

Signature Processing Flow

1. Capturing & Normalizing Signature Ink

To ensure the signature renders clearly on white certificate paper regardless of whether the user signed in Light Mode or Dark Mode, the frontend converts all strokes to black ink before saving:

function getBlackInkBase64(sourceCanvas) {
const offCanvas = document.createElement('canvas');
offCanvas.width = sourceCanvas.width;
offCanvas.height = sourceCanvas.height;
const ctx = offCanvas.getContext('2d');
ctx.drawImage(sourceCanvas, 0, 0);

const imgData = ctx.getImageData(0, 0, offCanvas.width, offCanvas.height);
const data = imgData.data;

// Force non-transparent pixels to RGB(0,0,0)
for (let i = 0; i < data.length; i += 4) {
if (data[i + 3] > 0) {
data[i] = 0; // Red
data[i + 1] = 0; // Green
data[i + 2] = 0; // Blue
}
}

ctx.putImageData(imgData, 0, 0);
return offCanvas.toDataURL('image/png');
}

2. Rendering in Template Engine

In templates/render.blade.php, signature fields are automatically detected and rendered as <img> elements with a subtle drop-shadow filter:

@elseif($isImageData)
<img src="{{ $val }}" class="el-img" style="object-fit: contain; width: 100%; height: 100%; filter: drop-shadow(0 0 1px rgba(0,0,0,0.6));">