useDocument Hook

The useDocument hook provides read-only access to the current document state, optimized for components that only need to display document information.

Import

import { 
  useDocument, 
  useCurrentPageFields, 
  useSelectedField 
} from '@mims/sdk-react';

useDocument

Returns a subset of document state properties. This hook is optimized for read-only access and will only re-render when these specific properties change.

Basic Usagetsx
function DocumentStatus() {
  const {
    documentId,
    isLoading,
    error,
    currentPage,
    totalPages,
    isDirty,
  } = useDocument();

  if (isLoading) {
    return <LoadingSpinner />;
  }

  if (error) {
    return <ErrorMessage>{error}</ErrorMessage>;
  }

  return (
    <div className="document-status">
      <span>Document: {documentId}</span>
      <span>Page {currentPage} of {totalPages}</span>
      {isDirty && <Badge variant="warning">Unsaved Changes</Badge>}
    </div>
  );
}

Return Value

PropTypeDefaultDescription
documentIdstring | nullThe unique identifier of the loaded document.
documentUrlstring | nullThe URL of the PDF document being displayed.
isLoadingbooleanWhether the document is currently loading.
errorstring | nullError message if document loading failed.
totalPagesnumberTotal number of pages in the document.
currentPagenumberThe current page being viewed (1-indexed).
pagesPageInfo[]Array of page information objects with dimensions.
isDirtybooleanWhether the document has unsaved changes.

useCurrentPageFields

Returns an array of FieldState objects for fields on the current page. Automatically updates when the page changes or fields are modified.

useCurrentPageFieldstsx
function FieldList() {
  const fields = useCurrentPageFields();

  return (
    <div className="field-list">
      <h3>Fields on this page ({fields.length})</h3>
      <ul>
        {fields.map((field) => (
          <li key={field.definition.id}>
            <span>{field.definition.label || field.definition.id}</span>
            <span className="type">{field.definition.type}</span>
            {field.definition.required && (
              <span className="required">Required</span>
            )}
            {field.touched && !field.value && (
              <span className="warning">Not filled</span>
            )}
          </li>
        ))}
      </ul>
    </div>
  );
}

FieldState Properties

PropTypeDefaultDescription
definitionAnyFieldDefinitionThe field definition including type, position, and configuration.
valueAnyFieldValue | nullThe current value of the field, or null if not filled.
touchedbooleanWhether the user has interacted with this field.
errorsstring[]Array of validation error messages for the field.

useSelectedField

Returns the currently selected field's state, or null if no field is selected.

useSelectedFieldtsx
function FieldInspector() {
  const selectedField = useSelectedField();

  if (!selectedField) {
    return (
      <div className="field-inspector empty">
        <p>Click a field to inspect its properties</p>
      </div>
    );
  }

  const { definition, value, touched, errors } = selectedField;

  return (
    <div className="field-inspector">
      <h3>{definition.label || 'Untitled Field'}</h3>
      
      <dl>
        <dt>Type</dt>
        <dd>{definition.type}</dd>
        
        <dt>Position</dt>
        <dd>({definition.x.toFixed(2)}, {definition.y.toFixed(2)})</dd>
        
        <dt>Size</dt>
        <dd>{definition.width.toFixed(2)} x {definition.height.toFixed(2)}</dd>
        
        <dt>Required</dt>
        <dd>{definition.required ? 'Yes' : 'No'}</dd>
        
        <dt>Status</dt>
        <dd>
          {!touched && 'Untouched'}
          {touched && value && 'Filled'}
          {touched && !value && 'Empty'}
        </dd>
      </dl>

      {errors.length > 0 && (
        <div className="errors">
          {errors.map((error, i) => (
            <p key={i} className="error">{error}</p>
          ))}
        </div>
      )}
    </div>
  );
}

Combining Hooks

These hooks work well together for building comprehensive document UI:

Combined Exampletsx
function DocumentSidebar() {
  const { currentPage, totalPages, isDirty } = useDocument();
  const fields = useCurrentPageFields();
  const selectedField = useSelectedField();

  const requiredFields = fields.filter(f => f.definition.required);
  const filledRequired = requiredFields.filter(f => f.value !== null);
  const progress = requiredFields.length > 0 
    ? (filledRequired.length / requiredFields.length) * 100 
    : 100;

  return (
    <aside className="document-sidebar">
      {/* Progress Section */}
      <section>
        <h4>Progress</h4>
        <ProgressBar value={progress} />
        <p>{filledRequired.length} of {requiredFields.length} required fields</p>
      </section>

      {/* Navigation */}
      <section>
        <h4>Page {currentPage} of {totalPages}</h4>
        <p>{fields.length} fields on this page</p>
      </section>

      {/* Selected Field Details */}
      {selectedField && (
        <section>
          <h4>Selected Field</h4>
          <p>{selectedField.definition.type}: {selectedField.definition.label}</p>
        </section>
      )}

      {/* Save Status */}
      {isDirty && (
        <section className="save-status">
          <p>You have unsaved changes</p>
        </section>
      )}
    </aside>
  );
}

Performance Tip

Use useDocument when you only need read-only document state. For actions like navigation or field manipulation, use useDocumentStore instead.

TypeScript Interfaces

types.tstypescript
interface PageInfo {
  /** Page number (1-indexed) */
  pageNumber: number;
  /** Original PDF page width in points */
  width: number;
  /** Original PDF page height in points */
  height: number;
  /** Page rotation in degrees */
  rotation: number;
}

interface FieldState {
  definition: AnyFieldDefinition;
  value: AnyFieldValue | null;
  touched: boolean;
  errors: string[];
}

type AnyFieldDefinition =
  | TextFieldDefinition
  | SignatureFieldDefinition
  | CheckboxFieldDefinition
  | DateFieldDefinition
  | InitialsFieldDefinition;

type AnyFieldValue =
  | TextFieldValue
  | SignatureFieldValue
  | CheckboxFieldValue
  | DateFieldValue
  | InitialsFieldValue;

Related Hooks