use crate::bindgen::{FPDF_DOCUMENT, FPDF_PAGEOBJECT};
use crate::bindings::PdfiumLibraryBindings;
use crate::error::{PdfiumError, PdfiumInternalError};
use crate::pdf::document::page::object::private::internal::PdfPageObjectPrivate;
use crate::pdf::document::page::object::{PdfPageObject, PdfPageObjectOwnership};
use crate::pdf::document::page::objects::common::{PdfPageObjectIndex, PdfPageObjectsIterator};
use crate::pdf::document::page::objects::private::internal::PdfPageObjectsPrivate;
use crate::pdf::matrix::{PdfMatrix, PdfMatrixValue};
use crate::pdf::points::PdfPoints;
use crate::{create_transform_getters, create_transform_setters};
use std::ops::{Range, RangeInclusive};
use std::os::raw::c_ulong;
#[cfg(doc)]
use {
crate::pdf::document::page::object::group::PdfPageGroupObject,
crate::pdf::document::page::object::PdfPageObjectType,
crate::pdf::document::page::objects::PdfPageObjects,
};
pub struct PdfPageXObjectFormObject<'a> {
object_handle: FPDF_PAGEOBJECT,
ownership: PdfPageObjectOwnership,
bindings: &'a dyn PdfiumLibraryBindings,
}
impl<'a> PdfPageXObjectFormObject<'a> {
pub(crate) fn from_pdfium(
object_handle: FPDF_PAGEOBJECT,
ownership: PdfPageObjectOwnership,
bindings: &'a dyn PdfiumLibraryBindings,
) -> Self {
PdfPageXObjectFormObject {
object_handle,
ownership,
bindings,
}
}
#[inline]
pub fn len(&self) -> PdfPageObjectIndex {
self.len_impl()
}
#[inline]
pub fn is_empty(&self) -> bool {
self.len() == 0
}
#[inline]
pub fn as_range(&self) -> Range<PdfPageObjectIndex> {
0..self.len()
}
#[inline]
pub fn as_range_inclusive(&self) -> RangeInclusive<PdfPageObjectIndex> {
if self.is_empty() {
0..=0
} else {
0..=(self.len() - 1)
}
}
#[inline]
pub fn get(&self, index: PdfPageObjectIndex) -> Result<PdfPageObject<'a>, PdfiumError> {
self.get_impl(index)
}
#[inline]
pub fn first(&self) -> Result<PdfPageObject<'a>, PdfiumError> {
if !self.is_empty() {
self.get(0)
} else {
Err(PdfiumError::NoPageObjectsInCollection)
}
}
#[inline]
pub fn last(&self) -> Result<PdfPageObject<'a>, PdfiumError> {
if !self.is_empty() {
self.get(self.len() - 1)
} else {
Err(PdfiumError::NoPageObjectsInCollection)
}
}
#[inline]
pub fn iter(&'a self) -> PdfPageObjectsIterator<'a> {
self.iter_impl()
}
create_transform_setters!(
&mut Self,
Result<(), PdfiumError>,
"this [PdfPageXObjectFormObject]",
"this [PdfPageXObjectFormObject].",
"this [PdfPageXObjectFormObject],"
);
create_transform_getters!(
"this [PdfPageXObjectFormObject]",
"this [PdfPageXObjectFormObject].",
"this [PdfPageXObjectFormObject],"
);
}
impl<'a> PdfPageObjectPrivate<'a> for PdfPageXObjectFormObject<'a> {
#[inline]
fn object_handle(&self) -> FPDF_PAGEOBJECT {
self.object_handle
}
#[inline]
fn ownership(&self) -> &PdfPageObjectOwnership {
&self.ownership
}
#[inline]
fn set_ownership(&mut self, ownership: PdfPageObjectOwnership) {
self.ownership = ownership;
}
#[inline]
fn bindings(&self) -> &dyn PdfiumLibraryBindings {
self.bindings
}
#[inline]
fn is_copyable_impl(&self) -> bool {
false
}
#[inline]
fn try_copy_impl<'b>(
&self,
_: FPDF_DOCUMENT,
_: &'b dyn PdfiumLibraryBindings,
) -> Result<PdfPageObject<'b>, PdfiumError> {
Err(PdfiumError::PageObjectNotCopyable)
}
}
impl<'a> PdfPageObjectsPrivate<'a> for PdfPageXObjectFormObject<'a> {
#[inline]
fn ownership(&self) -> &PdfPageObjectOwnership {
&self.ownership
}
#[inline]
fn bindings(&self) -> &'a dyn PdfiumLibraryBindings {
self.bindings
}
#[inline]
fn len_impl(&self) -> PdfPageObjectIndex {
self.bindings.FPDFFormObj_CountObjects(self.object_handle) as PdfPageObjectIndex
}
fn get_impl(&self, index: PdfPageObjectIndex) -> Result<PdfPageObject<'a>, PdfiumError> {
let object_handle = self
.bindings
.FPDFFormObj_GetObject(self.object_handle, index as c_ulong);
if object_handle.is_null() {
if index >= self.len() {
Err(PdfiumError::PageObjectIndexOutOfBounds)
} else {
Err(PdfiumError::PdfiumLibraryInternalError(
PdfiumInternalError::Unknown,
))
}
} else {
Ok(PdfPageObject::from_pdfium(
object_handle,
*PdfPageObjectPrivate::ownership(self),
PdfPageObjectsPrivate::bindings(self),
))
}
}
#[inline]
fn iter_impl(&'a self) -> PdfPageObjectsIterator<'a> {
PdfPageObjectsIterator::new(self)
}
fn add_object_impl(
&mut self,
_object: PdfPageObject<'a>,
) -> Result<PdfPageObject<'a>, PdfiumError> {
Err(PdfiumError::PageObjectsCollectionIsImmutable)
}
#[cfg(any(feature = "pdfium_future", feature = "pdfium_7350"))]
fn remove_object_impl(
&mut self,
mut object: PdfPageObject<'a>,
) -> Result<PdfPageObject<'a>, PdfiumError> {
if self.bindings.is_true(
self.bindings
.FPDFFormObj_RemoveObject(self.object_handle, object.object_handle()),
) {
object.set_ownership(PdfPageObjectOwnership::Unowned);
Ok(object)
} else {
Err(PdfiumError::PdfiumLibraryInternalError(
PdfiumInternalError::Unknown,
))
}
}
#[cfg(not(any(feature = "pdfium_future", feature = "pdfium_7350")))]
fn remove_object_impl(
&mut self,
_object: PdfPageObject<'a>,
) -> Result<PdfPageObject<'a>, PdfiumError> {
Err(PdfiumError::PageObjectsCollectionIsImmutable)
}
}
impl<'a> Drop for PdfPageXObjectFormObject<'a> {
fn drop(&mut self) {
self.drop_impl();
}
}