# @jaymanyoo/pdf-book-viewer

A React-compatible library for displaying PDFs as realistic flip books with 3D page turning animations.

## Features

- 🔄 **Realistic page flipping** - Smooth 3D animations using PageFlip library
- 📄 **Smart page handling** - Automatically detects portrait vs landscape pages
- 📱 **Mobile friendly** - Touch/swipe gestures and responsive design
- ⌨️ **Keyboard navigation** - Arrow keys for page navigation
- 🎨 **Customizable** - Configurable dimensions and animations
- 🚀 **Easy integration** - Simple API, works with any PDF source
- ⚛️ **React support** - Full React component with TypeScript support

## Installation

```bash
npm install @jaymanyoo/pdf-book-viewer pdfjs-dist
# or
yarn add @jaymanyoo/pdf-book-viewer pdfjs-dist
```

**Note:** `pdfjs-dist` is a required peer dependency that must be installed separately.

## Quick Start

### React Usage

```jsx
import React, { useState } from 'react';
import { ReactPDFBookViewer } from '@jaymanyoo/pdf-book-viewer/react';

function App() {
  const [selectedFile, setSelectedFile] = useState(null);

  const handleFileSelect = (event) => {
    const file = event.target.files?.[0];
    if (file && file.type === 'application/pdf') {
      setSelectedFile(file);
    }
  };

  return (
    <div>
      <input type="file" accept=".pdf" onChange={handleFileSelect} />
      
      {selectedFile && (
        <ReactPDFBookViewer
          source={selectedFile}
          width={800}
          height={600}
          onPageChange={(page, total) => {
            console.log(`Page ${page} of ${total}`);
          }}
          onLoadStart={() => console.log('Loading...')}
          onLoadEnd={() => console.log('Loaded!')}
          onError={(error) => console.error('Error:', error)}
        />
      )}
    </div>
  );
}
```

### Loading from URL

```jsx
<ReactPDFBookViewer
  source="https://example.com/document.pdf"
  width={800}
  height={600}
  onPageChange={(page, total) => {
    console.log(`Page ${page} of ${total}`);
  }}
/>
```

### TypeScript Support

```tsx
import React, { useRef } from 'react';
import { ReactPDFBookViewer, PDFBookViewerMethods, ReactPDFBookViewerProps } from '@jaymanyoo/pdf-book-viewer/react';

interface MyViewerProps {
  pdfUrl: string;
  onComplete?: () => void;
}

const MyTypedViewer: React.FC<MyViewerProps> = ({ pdfUrl, onComplete }) => {
  const viewerRef = useRef<PDFBookViewerMethods>(null);

  const handleNextPage = () => {
    viewerRef.current?.nextPage();
  };

  const handlePrevPage = () => {
    viewerRef.current?.prevPage();
  };

  return (
    <div>
      <button onClick={handlePrevPage}>Previous</button>
      <button onClick={handleNextPage}>Next</button>
      
      <ReactPDFBookViewer
        ref={viewerRef}
        source={pdfUrl}
        width={800}
        height={600}
        onLoadEnd={onComplete}
      />
    </div>
  );
};
```

## Props

| Prop | Type | Default | Description |
|------|------|---------|-------------|
| `source` | `string \| File` | - | PDF source (URL or File object) |
| `width` | `number` | `400` | Viewer width in pixels |
| `height` | `number` | `600` | Viewer height in pixels |
| `onPageChange` | `(page: number, total: number) => void` | - | Called when page changes |
| `onLoadStart` | `() => void` | - | Called when PDF loading starts |
| `onLoadEnd` | `() => void` | - | Called when PDF loading completes |
| `onError` | `(error: Error) => void` | - | Called when an error occurs |
| `style` | `React.CSSProperties` | - | Custom styles for the container |
| `className` | `string` | `''` | CSS class for the container |

## Ref Methods

When using a ref, you can access these methods:

```tsx
const viewerRef = useRef<PDFBookViewerMethods>(null);

// Navigation
viewerRef.current?.nextPage();        // Go to next page
viewerRef.current?.prevPage();        // Go to previous page
viewerRef.current?.goToPage(5);       // Go to specific page

// Loading
viewerRef.current?.load(file);        // Load new PDF

// State
const current = viewerRef.current?.getCurrentPage(); // Get current page
const total = viewerRef.current?.getTotalPages();    // Get total pages

// Cleanup
viewerRef.current?.destroy();         // Clean up resources
```

## Import Paths

```javascript
// React component
import { ReactPDFBookViewer } from '@jaymanyoo/pdf-book-viewer/react';

// TypeScript types
import type { 
  ReactPDFBookViewerProps,
  PDFBookViewerMethods
} from '@jaymanyoo/pdf-book-viewer/react';
```

## Page Handling

The viewer automatically handles different page orientations:

- **Portrait pages**: First/middle pages show on the right with transparent left, last page shows on left with transparent right
- **Landscape pages**: Automatically split into left and right halves
- **Mixed orientations**: Seamlessly handles PDFs with both portrait and landscape pages

## Interactions

- **Mouse**: Click and drag to flip pages
- **Touch**: Swipe gestures on mobile devices  
- **Keyboard**: Arrow keys for navigation (when focused)

## Browser Support

- Chrome 60+
- Firefox 55+
- Safari 12+
- Edge 79+

## Dependencies

- **pdfjs-dist** (peer dependency) - For PDF rendering
- **PageFlip library** - Automatically loaded from CDN for 3D animations
- **React** (peer dependency) - For React components

## Examples

Complete example with file upload and URL loading:

```jsx
import React, { useState } from 'react';
import { ReactPDFBookViewer } from '@jaymanyoo/pdf-book-viewer/react';

function PDFViewerExample() {
  const [selectedFile, setSelectedFile] = useState(null);
  const [urlInput, setUrlInput] = useState('');

  const handleFileSelect = (event) => {
    const file = event.target.files?.[0];
    if (file && file.type === 'application/pdf') {
      setSelectedFile(file);
    }
  };

  const loadFromURL = () => {
    if (urlInput.trim()) {
      setSelectedFile(urlInput.trim());
    }
  };

  const loadSample = () => {
    const sampleURL = 'https://mozilla.github.io/pdf.js/web/compressed.tracemonkey-pldi-09.pdf';
    setSelectedFile(sampleURL);
    setUrlInput(sampleURL);
  };

  return (
    <div style={{ padding: '20px' }}>
      <div style={{ marginBottom: '20px' }}>
        <h3>Upload PDF File</h3>
        <input type="file" accept=".pdf" onChange={handleFileSelect} />
      </div>

      <div style={{ marginBottom: '20px' }}>
        <h3>Load from URL</h3>
        <input
          type="text"
          value={urlInput}
          onChange={(e) => setUrlInput(e.target.value)}
          placeholder="Enter PDF URL"
          style={{ width: '300px', marginRight: '10px' }}
        />
        <button onClick={loadFromURL}>Load</button>
      </div>

      <div style={{ marginBottom: '20px' }}>
        <button onClick={loadSample}>Load Sample PDF</button>
      </div>

      {selectedFile && (
        <ReactPDFBookViewer
          source={selectedFile}
          width={800}
          height={600}
          onPageChange={(page, total) => {
            console.log(`Page ${page} of ${total}`);
          }}
          onLoadStart={() => console.log('Loading PDF...')}
          onLoadEnd={() => console.log('PDF loaded successfully!')}
          onError={(error) => console.error('PDF loading error:', error)}
        />
      )}
    </div>
  );
}

export default PDFViewerExample;
```

## License

MIT License