Skip to content

Latest commit

 

History

History
387 lines (350 loc) · 9.05 KB

File metadata and controls

387 lines (350 loc) · 9.05 KB

PdfViewer

A lightweight Android PDF viewer library powered by Mozilla's PDF.js, offering seamless PDF rendering and interactive features. Supports both Jetpack Compose and Xml.

For setup see Setup
For XML examples see XML Examples

Compose Examples

Simple Pdf Viewer

@Composable
fun SimplePdfViewer() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewer(
        pdfState = pdfState,
        modifier = Modifier
    )
}

Changing container color

@Composable
fun PdfViewerContainerColor() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewer(
        pdfState = pdfState,
        modifier = Modifier,
        containerColor = Color.Transparent
    )
}

Default onReady callback

@Composable
fun PdfViewerDefaultOnReadyCallback() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewer(
        pdfState = pdfState,
        modifier = Modifier,
        onReady = DefaultOnReadyCallback { // this: PdfViewer
            // loadSource is called before this callback
        }
    )
}

Custom onReady callback

@Composable
fun PdfViewerCustomOnReadyCallback() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewer(
        pdfState = pdfState,
        modifier = Modifier,
        onReady = CustomOnReadyCallback { loadSource ->  // this: PdfViewer
            loadSource()           // Mandatory to call
        }
    )
}

With PdfViewerContainer

@Composable
fun PdfViewerWithContainer() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {// this: PdfContainerBoxScope
            PdfViewer(             // pdfState is passed by PdfContainerBoxScope
                modifier = Modifier,
            )
        }
    )
}

With ToolBar and ScrollBar

@Composable
fun PdfViewerWithToolBarAndScrollBar() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier
            )
        },
        pdfToolBar = {
            PdfToolBar(
                title = "Title",
            )
        },
        pdfScrollBar = { parentSize ->
            PdfScrollBar(
                parentSize = parentSize
            )
        },
    )
}

ToolBar back icon

@Composable
fun ToolBarBack() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier
            )
        },
        pdfToolBar = {
            PdfToolBar(
                title = "Title",
                onBack = {
                    // called when back is clicked
                },
//                backIcon = { // this: PdfToolBarScope
//                    // or create your own back icon
//                }
            )
        },
        pdfScrollBar = { parentSize ->
            PdfScrollBar(
                parentSize = parentSize
            )
        },
    )
}

Listening for findBar state

@Composable
fun ListeningForFindBarState() {
    val pdfState = rememberPdfState("asset://sample.pdf")
    val toolBarState = rememberToolBarState()

    LaunchedEffect(toolBarState.isFindBarOpen) {
        // Do something
    }
    BackHandler {
        if (toolBarState.isFindBarOpen)
            toolBarState.isFindBarOpen = false
    }

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier
            )
        },
        pdfToolBar = {
            PdfToolBar(
                title = "Title",
                toolBarState = toolBarState,
            )
        },
        pdfScrollBar = { parentSize ->
            PdfScrollBar(
                parentSize = parentSize
            )
        },
    )
}

Extended ToolBar

@Composable
fun ExtendedToolBar() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier
            )
        },
        pdfToolBar = {
            PdfToolBar(
                title = "Title",
                dropDownMenu = { onDismiss, defaultMenus ->
                    ExtendedTooBarMenus(
                        onDismiss = onDismiss,
                        defaultMenus = defaultMenus
                    )
                }
            )
        },
        pdfScrollBar = { parentSize ->
            PdfScrollBar(
                parentSize = parentSize
            )
        },
    )
}

@Composable
private fun ExtendedTooBarMenus(
    onDismiss: () -> Unit,
    defaultMenus: @Composable (filtered: List<PdfToolBarMenuItem>) -> Unit
) {
    DropdownMenuItem(
        text = { Text(text = "Extended Menu") },
        onClick = {
            // Do something
            onDismiss()
        }
    )
    defaultMenus(PdfToolBarMenuItem.entries)
    // or defaultMenus(PdfToolBarMenuItem.entries.filter { it != PdfToolBarMenuItem.CUSTOM_PAGE_ARRANGEMENT })
}

Colors

@Composable
fun Colors() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier,
                containerColor = Color.Red
            )
        },
        pdfToolBar = {
            PdfToolBar(
                title = "Title",
                contentColor = Color.Blue,
            )
        },
        pdfScrollBar = { parentSize ->
            PdfScrollBar(
                parentSize = parentSize,
                contentColor = Color.Blue,
                handleColor = Color.Green
            )
        },
    )
}

Customize ScrollBar

@Composable
fun CustomizeScrollBar() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier,
            )
        },
        pdfToolBar = {
            PdfToolBar(
                title = "Title",
            )
        },
        pdfScrollBar = { parentSize ->
            PdfScrollBar(
                parentSize = parentSize,
                useVerticalScrollBarForHorizontalMode = true,
                interactiveScrolling = true,
            )
        },
    )
}

Loading Indicator

@Composable
fun LoadingIndicator() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewerContainer(
        pdfState = pdfState,
        pdfViewer = {
            PdfViewer(
                modifier = Modifier,
            )
        },
        loadingIndicator = {
            Column(
                Modifier
                    .fillMaxSize()
                    .background(MaterialTheme.colorScheme.background),
                verticalArrangement = Arrangement.Center,
                horizontalAlignment = Alignment.CenterHorizontally,
            ) {
                CircularProgressIndicator()
                Text(text = "Loading...")
            }
        },
    )
}

Factory

@Composable
fun PdfViewerFactoryCallback() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewer(
        pdfState = pdfState,
        modifier = Modifier,
        factory = { context ->
            PdfViewer(context) // return PdfViewer instance.
        }
    )
}

Use factory for create PdfViewer instance and use onCreateViewer for configuring

Listener and onCreateViewer callback

@Composable
fun PdfViewerOnCreateViewerCallback() {
    val pdfState = rememberPdfState("asset://sample.pdf")

    PdfViewer(
        pdfState = pdfState,
        modifier = Modifier,
        onCreateViewer = { // this: PdfViewer
            // You can add listener with extension like
            addListener(onPageLoadFailed = {
            })
            // or
            addListener(object: PdfListener {
                // implement required methods
            })
        }
    )
}

Note

For Download listener see implementation in PdfViewerActivity.kt

States that PdfState provides

  1. source: String
  2. pdfViewer: PdfViewer?
  3. loadingState: PdfLoadingState
  4. pagesCount: Int
  5. currentPage: Int
  6. currentScale: Float
  7. properties: PdfDocumentProperties?
  8. passwordRequired: Boolean
  9. scrollState: ScrollState
  10. matchState: MatchState
  11. scrollMode: PdfViewer.PageScrollMode
  12. spreadMode: PdfViewer.PageSpreadMode
  13. rotation: PdfViewer.PageRotation
  14. scaleLimit: ScaleLimit
  15. actualScaleLimit: ActualScaleLimit
  16. snapPage: Boolean
  17. singlePageArrangement: Boolean
  18. alignMode: PdfViewer.PageAlignMode
  19. scrollSpeedLimit

See Also

  1. Implementations
  2. PdfViewer public members