React PDF viewer
v1.6.0

Example: Preview a document inside a modal

In this example, we will see how to preview a PDF document in a full screen modal.

Create a modal

It's easy to create a modal with React. First of all, we need a flag to track if the modal is opened or not:

import { useState } from 'react';

const [shown, setShown] = useState(false);

The modal usually can be opened by triggering the click event of a button. The event handler simply calls setShown(true):

<button onClick={() => setShown(true)}>Open modal</button>

The modal then is attached to the body element:

const modalBody = () => (
    // Build the modal body
    // ...
);

return (
    <>
        <button onClick={() => setShown(true)}>Open modal</button>
        {shown && ReactDOM.createPortal(modalBody(), document.body)}
    </>
);

In order to make the modal take full screen size, we need to add some CSS styles to the modal:

const modalBody = () => (
    <div
        style={{
            backgroundColor: '#fff',

            /* Fixed position */
            left: 0,
            position: 'fixed',
            top: 0,

            /* Take full size */
            height: '100%',
            width: '100%',

            /* Displayed on top of other elements */
            zIndex: 9999,

            /* Make the content scrollable */
            overflow: 'auto',
        }}
    >
        <!-- We will display viewer here -->
        ...
    </div>
);

Customize the toolbar

It's recommended to take a look at this example example to see how we can create a customized toolbar.

In this example, we add a button to the toolbar to close the modal:

import {
    Button,
    Position,
    RenderToolbar,
    Slot,
    ToolbarSlot,
    Tooltip,
} from '@phuocng/react-pdf-viewer';

const renderToolbar = (toolbarSlot: ToolbarSlot): React.ReactElement => {
    return (
        <div
            style={{
                alignItems: 'center',
                display: 'flex',
                width: '100%',
            }}
        >
            <div
                style={{
                    alignItems: 'center',
                    display: 'flex',
                    flexGrow: 1,
                    flexShrink: 1,
                    justifyContent: 'center',
                }}
            >
                /* Some built-in buttons */
                <div style={{ marginLeft: 'auto', padding: '0 2px' }}>
                    {toolbarSlot.previousPageButton}
                </div>
                
                /* ... */
                
                /* The close button */
                <div style={{ marginLeft: 'auto', padding: '0 2px' }}>
                    <Tooltip
                        position={Position.BottomRight}
                        target={<Button onClick={() => setShown(false)}><CloseIcon /></Button>}
                        content={() => "Close"}
                        offset={{ left: 0, top: 8 }}
                    />
                </div>
            </div>
        </div>
    );
};

As you see in the sample code above, the close button is built on top of other components such as Tooltip, Button, Icon which are provided by the viewer.

It makes the button looks similar to other toolbar buttons. Of course, it's up to you to build your own button, even with a button tag:

const renderToolbar = (toolbarSlot: ToolbarSlot): React.ReactElement => {
    return (
        ...
        <button onClick={() => setShown(false)}>Close</button>
    );
};

Now the toolbar is ready. We can create a custom layout and pass it to the viewer:

import Viewer, {
    defaultLayout,
    RenderToolbar,
    Slot,
} from '@phuocng/react-pdf-viewer';

const layout = (
    isSidebarOpened: boolean,
    container: Slot,
    main: Slot,
    toolbar: RenderToolbar,
    sidebar: Slot,
): React.ReactElement => {
    return defaultLayout(
        isSidebarOpened,
        container,
        main,
        toolbar(renderToolbar),
        sidebar,
    );
};

const modalBody = () => (
    <Viewer fileUrl="/path/to/document.pdf" layout={layout} />
);

(The sample code)