pdfium_render/pdf/document/page/object/
x_object_form.rs1use crate::bindgen::FPDF_PAGEOBJECT;
5use crate::error::{PdfiumError, PdfiumInternalError};
6use crate::pdf::document::page::object::private::internal::PdfPageObjectPrivate;
7use crate::pdf::document::page::object::{PdfPageObject, PdfPageObjectOwnership};
8use crate::pdf::document::page::objects::common::{PdfPageObjectIndex, PdfPageObjectsIterator};
9use crate::pdf::document::page::objects::private::internal::PdfPageObjectsPrivate;
10use crate::pdf::matrix::{PdfMatrix, PdfMatrixValue};
11use crate::pdf::points::PdfPoints;
12use crate::pdfium::PdfiumLibraryBindingsAccessor;
13use crate::{create_transform_getters, create_transform_setters};
14use std::marker::PhantomData;
15use std::ops::{Range, RangeInclusive};
16use std::os::raw::c_ulong;
17
18#[cfg(doc)]
19use {
20 crate::pdf::document::page::object::group::PdfPageGroupObject,
21 crate::pdf::document::page::object::PdfPageObjectType,
22 crate::pdf::document::page::objects::PdfPageObjects,
23};
24
25pub struct PdfPageXObjectFormObject<'a> {
37 object_handle: FPDF_PAGEOBJECT,
38 ownership: PdfPageObjectOwnership,
39 lifetime: PhantomData<&'a FPDF_PAGEOBJECT>,
40}
41
42impl<'a> PdfPageXObjectFormObject<'a> {
43 pub(crate) fn from_pdfium(
44 object_handle: FPDF_PAGEOBJECT,
45 ownership: PdfPageObjectOwnership,
46 ) -> Self {
47 PdfPageXObjectFormObject {
48 object_handle,
49 ownership,
50 lifetime: PhantomData,
51 }
52 }
53
54 #[inline]
56 pub fn len(&self) -> PdfPageObjectIndex {
57 self.len_impl()
58 }
59
60 #[inline]
62 pub fn is_empty(&self) -> bool {
63 self.len() == 0
64 }
65
66 #[inline]
69 pub fn as_range(&self) -> Range<PdfPageObjectIndex> {
70 0..self.len()
71 }
72
73 #[inline]
76 pub fn as_range_inclusive(&self) -> RangeInclusive<PdfPageObjectIndex> {
77 if self.is_empty() {
78 0..=0
79 } else {
80 0..=(self.len() - 1)
81 }
82 }
83
84 #[inline]
86 pub fn get(&self, index: PdfPageObjectIndex) -> Result<PdfPageObject<'a>, PdfiumError> {
87 self.get_impl(index)
88 }
89
90 #[inline]
92 pub fn first(&self) -> Result<PdfPageObject<'a>, PdfiumError> {
93 if !self.is_empty() {
94 self.get(0)
95 } else {
96 Err(PdfiumError::NoPageObjectsInCollection)
97 }
98 }
99
100 #[inline]
102 pub fn last(&self) -> Result<PdfPageObject<'a>, PdfiumError> {
103 if !self.is_empty() {
104 self.get(self.len() - 1)
105 } else {
106 Err(PdfiumError::NoPageObjectsInCollection)
107 }
108 }
109
110 #[inline]
112 pub fn iter(&'a self) -> PdfPageObjectsIterator<'a> {
113 self.iter_impl()
114 }
115
116 create_transform_setters!(
117 &mut Self,
118 Result<(), PdfiumError>,
119 "this [PdfPageXObjectFormObject]",
120 "this [PdfPageXObjectFormObject].",
121 "this [PdfPageXObjectFormObject],"
122 );
123
124 create_transform_getters!(
128 "this [PdfPageXObjectFormObject]",
129 "this [PdfPageXObjectFormObject].",
130 "this [PdfPageXObjectFormObject],"
131 );
132
133 }
136
137impl<'a> PdfPageObjectPrivate<'a> for PdfPageXObjectFormObject<'a> {
138 #[inline]
139 fn object_handle(&self) -> FPDF_PAGEOBJECT {
140 self.object_handle
141 }
142
143 #[inline]
144 fn ownership(&self) -> &PdfPageObjectOwnership {
145 &self.ownership
146 }
147
148 #[inline]
149 fn set_ownership(&mut self, ownership: PdfPageObjectOwnership) {
150 self.ownership = ownership;
151 }
152}
153
154impl<'a> PdfPageObjectsPrivate<'a> for PdfPageXObjectFormObject<'a> {
155 #[inline]
156 fn ownership(&self) -> &PdfPageObjectOwnership {
157 &self.ownership
158 }
159
160 #[inline]
161 fn len_impl(&self) -> PdfPageObjectIndex {
162 (unsafe { self.bindings().FPDFFormObj_CountObjects(self.object_handle) })
163 as PdfPageObjectIndex
164 }
165
166 fn get_impl(&self, index: PdfPageObjectIndex) -> Result<PdfPageObject<'a>, PdfiumError> {
167 let object_handle = unsafe {
168 self.bindings()
169 .FPDFFormObj_GetObject(self.object_handle, index as c_ulong)
170 };
171
172 if object_handle.is_null() {
173 if index >= self.len() {
174 Err(PdfiumError::PageObjectIndexOutOfBounds)
175 } else {
176 Err(PdfiumError::PdfiumLibraryInternalError(
177 PdfiumInternalError::Unknown,
178 ))
179 }
180 } else {
181 Ok(PdfPageObject::from_pdfium(
182 object_handle,
183 *PdfPageObjectPrivate::ownership(self),
184 PdfiumLibraryBindingsAccessor::bindings(self),
185 ))
186 }
187 }
188
189 #[inline]
190 fn iter_impl(&'a self) -> PdfPageObjectsIterator<'a> {
191 PdfPageObjectsIterator::new(self)
192 }
193
194 fn add_object_impl(
197 &mut self,
198 _object: PdfPageObject<'a>,
199 ) -> Result<PdfPageObject<'a>, PdfiumError> {
200 Err(PdfiumError::PageObjectsCollectionIsImmutable)
201 }
202
203 #[cfg(any(
204 feature = "pdfium_future",
205 feature = "pdfium_7543",
206 feature = "pdfium_7350"
207 ))]
208 fn remove_object_impl(
209 &mut self,
210 mut object: PdfPageObject<'a>,
211 ) -> Result<PdfPageObject<'a>, PdfiumError> {
212 if self.bindings().is_true(unsafe {
213 self.bindings()
214 .FPDFFormObj_RemoveObject(self.object_handle, object.object_handle())
215 }) {
216 object.set_ownership(PdfPageObjectOwnership::Unowned);
217
218 Ok(object)
219 } else {
220 Err(PdfiumError::PdfiumLibraryInternalError(
221 PdfiumInternalError::Unknown,
222 ))
223 }
224 }
225
226 #[cfg(not(any(
227 feature = "pdfium_future",
228 feature = "pdfium_7543",
229 feature = "pdfium_7350"
230 )))]
231 fn remove_object_impl(
232 &mut self,
233 _object: PdfPageObject<'a>,
234 ) -> Result<PdfPageObject<'a>, PdfiumError> {
235 Err(PdfiumError::PageObjectsCollectionIsImmutable)
236 }
237}
238
239impl<'a> Drop for PdfPageXObjectFormObject<'a> {
240 fn drop(&mut self) {
242 self.drop_impl();
243 }
244}
245
246impl<'a> PdfiumLibraryBindingsAccessor<'a> for PdfPageXObjectFormObject<'a> {}
247
248#[cfg(feature = "thread_safe")]
249unsafe impl<'a> Send for PdfPageXObjectFormObject<'a> {}
250
251#[cfg(feature = "thread_safe")]
252unsafe impl<'a> Sync for PdfPageXObjectFormObject<'a> {}