npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@npoci/pdfform

v0.0.1-beta.16

Published

Modern PDF form renderer with HTML overlay fields - view, fill, and map PDF forms in the browser

Readme

@npoci/pdfform

Modern PDF form renderer with HTML overlay fields. View, fill, validate, and map PDF forms directly in the browser.

npm version License: MIT

Features

  • 🎯 HTML Overlay Fields - Real HTML inputs positioned over PDF forms
  • 📝 Form Filling - Fill and export PDF forms programmatically
  • 🔍 Field Mapping - Visual field mapper to create user-friendly field definitions
  • Validation - Built-in validation with custom patterns and error messages
  • 🎨 Customizable - Override field renderers and styles
  • 📦 Framework Agnostic - Works with React, Vue, Angular, or vanilla JS
  • 🔒 Type Safe - Full TypeScript support

Installation

npm install @npoci/pdfform

Quick Start

Basic PDF Form Renderer

import { PDFFormRenderer } from '@npoci/pdfform'

const renderer = new PDFFormRenderer({
  container: document.getElementById('pdf-container'),
  pdfUrl: 'path/to/form.pdf'
})

// Listen for field changes
renderer.on('fieldChange', (field, validationState) => {
  console.log(`${field.name}: ${field.value}`, validationState)
})

// Render the PDF
await renderer.render()

// Get form values
const values = renderer.getFieldValues()
// { email: '[email protected]', name: 'John Doe' }

// Get validation states
const states = renderer.getFieldStates()
// { email: { valid: true }, name: { valid: false, error: 'Required' } }

Field Definitions

Make PDF fields user-friendly with custom definitions:

const renderer = new PDFFormRenderer({
  container: document.getElementById('pdf-container'),
  pdfUrl: 'form.pdf',
  fieldDefinitions: [
    {
      key: 'field_12_a',  // Original PDF field name
      name: 'email',      // User-friendly name for getFieldValues()
      title: 'Email Address',
      placeholder: 'Enter your email',
      required: true,
      pattern: '^[^@]+@[^@]+\\.[^@]+$',
      errorMessage: 'Please enter a valid email'
    }
  ]
})

Custom Field Renderers

Override how specific fields are rendered:

const renderer = new PDFFormRenderer({
  container: document.getElementById('pdf-container'),
  pdfUrl: 'form.pdf',
  fieldOverrides: {
    'signature_field': {
      createField(field, bounds, setValue) {
        const canvas = document.createElement('canvas')
        canvas.width = bounds.width
        canvas.height = bounds.height
        // Add your signature drawing logic
        return canvas
      },
      getValue(element) {
        return element.toDataURL()
      },
      setValue(element, value) {
        // Load signature from data URL
      }
    }
  }
})

Fill and Download PDFs

import { PDFFiller } from '@npoci/pdfform'

const filler = new PDFFiller()
const values = renderer.getRawFieldValues()

// Fill the PDF
const filledPdfBytes = await filler.fillFromUrl('form.pdf', values)

// Download
const blob = new Blob([filledPdfBytes], { type: 'application/pdf' })
const url = URL.createObjectURL(blob)
const link = document.createElement('a')
link.href = url
link.download = 'filled-form.pdf'
link.click()

Field Mapper

Create field definitions visually with the built-in mapper:

import { PDFFieldMapper } from '@npoci/pdfform'

const mapper = new PDFFieldMapper({
  container: document.getElementById('mapper-container'),
  pdfUrl: 'form.pdf'
})

// Listen for field selection
mapper.on('fieldSelected', ({ field, currentMapping }) => {
  console.log('Selected:', field.key)
})

// Export field definitions
const definitions = mapper.getFieldDefinitions()
console.log(JSON.stringify(definitions, null, 2))

API Reference

PDFFormRenderer

Options

interface PDFFormRendererOptions {
  container: HTMLElement
  pdfUrl: string
  fieldDefinitions?: FieldDefinition[]
  fieldRenderers?: Record<string, FieldRenderer>
  fieldOverrides?: Record<string, FieldRenderer>
  scale?: number
  page?: number
  highlightColor?: string      // Default: '#ffffcc'
  highlightColorFocus?: string  // Default: '#ffffaa'
}

Methods

  • render(): Promise<void> - Render the PDF
  • setPage(pageNumber: number): void - Change page
  • getFieldValues(): Record<string, any> - Get form values with user-friendly names
  • getRawFieldValues(): Record<string, any> - Get values with original PDF field names
  • getFieldStates(): Record<string, ValidationState> - Get validation states
  • setFieldValues(values: Record<string, any>): void - Set multiple field values
  • destroy(): void - Clean up resources

Events

  • ready - PDF loaded and fields discovered
  • fieldChange - Field value changed with validation
  • pageChange - Page changed
  • error - Error occurred

PDFFieldMapper

Options

interface PDFFieldMapperOptions {
  container: HTMLElement
  pdfUrl: string
  fieldDefinitions?: FieldDefinition[]
}

Methods

  • render(): Promise<void> - Render the mapper
  • setFieldDefinition(key: string, definition: FieldDefinition): void - Map a field
  • removeFieldDefinition(key: string): void - Remove mapping
  • getFieldDefinitions(): FieldDefinition[] - Get all mappings
  • exportDefinitions(): string - Export as JSON
  • importDefinitions(json: string): void - Import mappings
  • clearMappings(): void - Clear all mappings

Browser Compatibility

  • Chrome/Edge 88+
  • Firefox 85+
  • Safari 14+

License

MIT © npoci

Contributing

Issues and PRs welcome! Please check existing issues before creating new ones.

Acknowledgments

Built on top of PDF.js and pdf-lib.