///|
fn PdfDocument::pdf_image_resolution_lookup_inline_int(
self : PdfDocument,
first_key : @core.PdfName,
second_key : @core.PdfName,
image : @syntax.PdfObject,
) -> Int? {
match self.lookup_direct_or_else(first_key, second_key, image) {
Some(PdfInteger(value)) => Some(value)
_ => None
}
}
///|
fn pdf_image_resolution_find_candidate(
candidates : ArrayView[PdfImageResolutionCandidate],
name : @core.PdfName,
) -> PdfImageResolutionCandidate? {
for candidate in candidates {
if candidate.name == name {
break Some(candidate)
}
} nobreak {
None
}
}
///|
fn PdfDocument::pdf_image_resolution_candidates(
self : PdfDocument,
resources : @syntax.PdfObject,
) -> Array[PdfImageResolutionCandidate] raise @core.PdfError {
match self.lookup_direct(pdf_image_xobject_key(), resources) {
Some(PdfDictionary(xobjects)) => {
let candidates : Array[PdfImageResolutionCandidate] = Array(
capacity=xobjects.length(),
)
for entry in xobjects {
let object_number = match entry.1 {
PdfIndirect(number) => number
_ => 0
}
match self.lookup_direct(pdf_image_subtype_key(), entry.1) {
Some(PdfNameObject(subtype)) if subtype == pdf_image_image_name() =>
candidates.push({
name: entry.0,
object: PdfImageResolutionImage(
self.pdf_image_lookup_int_or_default(
pdf_image_width_key(),
pdf_image_width_key(),
entry.1,
1,
),
self.pdf_image_lookup_int_or_default(
pdf_image_height_key(),
pdf_image_height_key(),
entry.1,
1,
),
),
object_number,
})
Some(PdfNameObject(subtype)) if subtype == pdf_image_form_name() => {
let form = self.direct(entry.1)
let form_resources = match
self.lookup_direct(pdf_xobject_resources_key(), form) {
Some(resources) => resources
None => resources
}
candidates.push({
name: entry.0,
object: PdfImageResolutionForm(
self.parse_matrix(pdf_image_matrix_key(), form),
form,
form_resources,
),
object_number,
})
}
_ => ()
}
}
candidates
}
_ => []
}
}
///|
fn PdfDocument::pdf_image_resolution_process_content(
self : PdfDocument,
resources : @syntax.PdfObject,
content : ArrayView[@syntax.PdfObject],
candidates : ArrayView[PdfImageResolutionCandidate],
page_number : Int,
inline : Bool,
initial_matrix : @geometry.TransformMatrix,
depth : Int,
results : Array[PdfImageResolutionEntry],
) -> Unit raise @core.PdfError {
if depth > 64 {
return
}
let ops = self.parse_content_ops_with_resources(resources, content)
let transforms : Array[@geometry.TransformMatrix] = [initial_matrix]
for op in ops {
match op {
Op_cm(matrix) =>
if transforms.length() > 0 {
let index = transforms.length() - 1
transforms[index] = @geometry.transform_matrix_compose(
transforms[index],
matrix,
)
}
Op_q =>
if transforms.length() > 0 {
transforms.push(transforms[transforms.length() - 1])
}
Op_Q => if transforms.length() > 0 { ignore(transforms.pop()) }
Op_InlineImage(dictionary, _, _) =>
if inline && transforms.length() > 0 {
match
(
self.pdf_image_resolution_lookup_inline_int(
pdf_image_width_key(),
pdf_image_w_key(),
dictionary,
),
self.pdf_image_resolution_lookup_inline_int(
pdf_image_height_key(),
pdf_image_h_key(),
dictionary,
),
) {
(Some(width), Some(height)) =>
pdf_image_resolution_push_entry(
results,
page_number,
pdf_image_name("/InlineImage"),
width,
height,
0,
transforms[transforms.length() - 1],
)
_ => ()
}
}
Op_Do(name) =>
if transforms.length() > 0 {
match pdf_image_resolution_find_candidate(candidates, name) {
Some(
{
object: PdfImageResolutionImage(width, height),
object_number,
..
}
) =>
pdf_image_resolution_push_entry(
results,
page_number,
name,
width,
height,
object_number,
transforms[transforms.length() - 1],
)
Some(
{
object: PdfImageResolutionForm(matrix, form, form_resources),
..
}
) => {
let form_candidates = self.pdf_image_resolution_candidates(
form_resources,
)
self.pdf_image_resolution_process_content(
form_resources,
[form],
form_candidates,
page_number,
inline,
@geometry.transform_matrix_compose(
matrix,
transforms[transforms.length() - 1],
),
depth + 1,
results,
)
}
None => ()
}
}
_ => ()
}
}
}