First stage of PMIN plus 3mm etc

This commit is contained in:
John Whitington 2016-07-21 17:02:11 +01:00
parent 43ffc25b9c
commit ff9e90cb36
3 changed files with 140 additions and 110 deletions

73
cpdf.ml
View File

@ -2082,17 +2082,18 @@ let change_pattern_matrices pdf tr resources =
with with
Pdftransform.NonInvertable -> resources Pdftransform.NonInvertable -> resources
let shift_page ?(fast=false) dx dy pdf _ page = let shift_page ?(fast=false) dxdylist pdf pnum page =
let transform_op = let dx, dy = List.nth dxdylist (pnum - 1) in
Pdfops.Op_cm (Pdftransform.matrix_of_op (Pdftransform.Translate (dx, dy))) let transform_op =
in Pdfops.Op_cm (Pdftransform.matrix_of_op (Pdftransform.Translate (dx, dy)))
let resources' =
change_pattern_matrices pdf (Pdftransform.mktranslate ~-.dx ~-.dy) page.Pdfpage.resources
in in
Pdfpage.prepend_operators pdf [transform_op] ~fast {page with Pdfpage.resources = resources'} let resources' =
change_pattern_matrices pdf (Pdftransform.mktranslate ~-.dx ~-.dy) page.Pdfpage.resources
in
Pdfpage.prepend_operators pdf [transform_op] ~fast {page with Pdfpage.resources = resources'}
let shift_pdf ?(fast=false) dx dy pdf range = let shift_pdf ?(fast=false) dxdylist pdf range =
process_pages (shift_page ~fast dx dy pdf) pdf range process_pages (shift_page ~fast dxdylist pdf) pdf range
(* Change a page's media box so its minimum x and y are 0, making other (* Change a page's media box so its minimum x and y are 0, making other
operations simpler to think about. Any shift that is done is reflected in operations simpler to think about. Any shift that is done is reflected in
@ -2106,7 +2107,7 @@ let rectify_boxes ?(fast=false) pdf page =
in in
let page = change_boxes f pdf page in let page = change_boxes f pdf page in
if minx <> 0. || miny <> 0. if minx <> 0. || miny <> 0.
then shift_page ~fast (-.minx) (-.miny) pdf 0 page then shift_page ~fast [(-.minx),(-.miny)] pdf 1 page
else page else page
(* \section{Flip pages} *) (* \section{Flip pages} *)
@ -2398,8 +2399,9 @@ let nobble_page pdf _ page =
do_stamp false false (BottomLeft 0.) false false false true pdf page' page (Pdf.empty ()) do_stamp false false (BottomLeft 0.) false false false true pdf page' page (Pdf.empty ())
(* \section{Set media box} *) (* \section{Set media box} *)
let set_mediabox x y w h pdf range = let set_mediabox xywhlist pdf range =
let crop_page _ page = let crop_page pnum page =
let x, y, w, h = List.nth xywhlist (pnum - 1) in
{page with {page with
Pdfpage.mediabox = Pdfpage.mediabox =
(Pdf.Array (Pdf.Array
@ -2419,16 +2421,17 @@ let setBox box minx maxx miny maxy pdf range =
process_pages set_box_page pdf range process_pages set_box_page pdf range
(* \section{Cropping} *) (* \section{Cropping} *)
let crop_pdf x y w h pdf range = let crop_pdf xywhlist pdf range =
let crop_page _ page = let crop_page pagenum page =
{page with {page with
Pdfpage.rest = Pdfpage.rest =
(Pdf.add_dict_entry (Pdf.add_dict_entry
page.Pdfpage.rest page.Pdfpage.rest
"/CropBox" "/CropBox"
(Pdf.Array (let x, y, w, h = List.nth xywhlist (pagenum - 1) in
[Pdf.Real x; Pdf.Real y; (Pdf.Array
Pdf.Real (x +. w); Pdf.Real (y +. h)]))} [Pdf.Real x; Pdf.Real y;
Pdf.Real (x +. w); Pdf.Real (y +. h)])))}
in in
process_pages crop_page pdf range process_pages crop_page pdf range
@ -2552,26 +2555,28 @@ let upright ?(fast=false) range pdf =
process_pages (upright_page pdf) pdf range process_pages (upright_page pdf) pdf range
(* \section{Scale page data} *) (* \section{Scale page data} *)
let scale_pdf ?(fast=false) sx sy pdf range = let scale_pdf ?(fast=false) sxsylist pdf range =
let scale_page _ page = let scale_page pnum page =
let f (xmin, ymin, xmax, ymax) = let sx, sy = List.nth sxsylist (pnum - 1) in
xmin *. sx, ymin *. sy, xmax *. sx, ymax *. sy let f (xmin, ymin, xmax, ymax) =
in xmin *. sx, ymin *. sy, xmax *. sx, ymax *. sy
let page = change_boxes f pdf page in
and matrix = Pdftransform.matrix_of_op (Pdftransform.Scale ((0., 0.), sx, sy)) in let page = change_boxes f pdf page
let transform_op = and matrix = Pdftransform.matrix_of_op (Pdftransform.Scale ((0., 0.), sx, sy)) in
Pdfops.Op_cm matrix let transform_op =
and resources' = Pdfops.Op_cm matrix
change_pattern_matrices pdf (Pdftransform.matrix_invert matrix) page.Pdfpage.resources and resources' =
in change_pattern_matrices pdf (Pdftransform.matrix_invert matrix) page.Pdfpage.resources
Pdfpage.prepend_operators pdf ~fast [transform_op] {page with Pdfpage.resources = resources'} in
in Pdfpage.prepend_operators pdf ~fast [transform_op] {page with Pdfpage.resources = resources'}
process_pages scale_page pdf range in
process_pages scale_page pdf range
(* Scale to fit page of size x * y *) (* Scale to fit page of size x * y *)
(* FIXME: Can we do this in terms of scale_contents - and then just fix up the boxes? For 1.8 *) (* FIXME: Can we do this in terms of scale_contents - and then just fix up the boxes? For 1.8 *)
let scale_to_fit_pdf ?(fast=false) input_scale x y op pdf range = let scale_to_fit_pdf ?(fast=false) input_scale xylist op pdf range =
let scale_page_to_fit _ page = let scale_page_to_fit pnum page =
let x, y = List.nth xylist (pnum - 1) in
let matrix = let matrix =
let (minx, miny, maxx, maxy) = let (minx, miny, maxx, maxy) =
(* Use cropbox if available *) (* Use cropbox if available *)

View File

@ -346,11 +346,11 @@ val output_page_info : Pdf.t -> int list -> unit
(** True if a given page in a PDF has a given box *) (** True if a given page in a PDF has a given box *)
val hasbox : Pdf.t -> int -> string -> bool val hasbox : Pdf.t -> int -> string -> bool
(** [crop_pdf x y w h pdf range] sets the cropbox on the given pages. *) (** [crop_pdf xywhlist pdf range] sets the cropbox on the given pages. *)
val crop_pdf : float -> float -> float -> float -> Pdf.t -> int list -> Pdf.t val crop_pdf : (float * float * float * float) list -> Pdf.t -> int list -> Pdf.t
(** [set_mediabox x y w h pdf range] sets the cropbox on the given pages. *) (** [set_mediabox xywhlist pdf range] sets the media box on the given pages. *)
val set_mediabox : float -> float -> float -> float -> Pdf.t -> int list -> Pdf.t val set_mediabox : (float * float * float * float) list -> Pdf.t -> int list -> Pdf.t
(** [setBox boxname x y w h pdf range] sets the given box on the given pages. *) (** [setBox boxname x y w h pdf range] sets the given box on the given pages. *)
val setBox : string -> float -> float -> float -> float -> Pdf.t -> int list -> Pdf.t val setBox : string -> float -> float -> float -> float -> Pdf.t -> int list -> Pdf.t
@ -385,16 +385,18 @@ val vflip_pdf : ?fast:bool -> Pdf.t -> int list -> Pdf.t
(** Flip the given pages horizontally *) (** Flip the given pages horizontally *)
val hflip_pdf : ?fast:bool -> Pdf.t -> int list -> Pdf.t val hflip_pdf : ?fast:bool -> Pdf.t -> int list -> Pdf.t
(** Shift a PDF in x and y (in pts) in the given pages. *) (** Shift a PDF in x and y (in pts) in the given pages. List of (x, y) pairs is
val shift_pdf : ?fast:bool -> float -> float -> Pdf.t -> int list -> Pdf.t for all pages in pdf. *)
val shift_pdf : ?fast:bool -> (float * float) list -> Pdf.t -> int list -> Pdf.t
(** Scale a PDF in sx, sy in the given pages. *) (** Scale a PDF in sx, sy in the given pages. List of (sx, sy) pairs is
val scale_pdf : ?fast:bool -> float -> float -> Pdf.t -> int list -> Pdf.t for all pages in pdf. *)
val scale_pdf : ?fast:bool -> (float * float) list -> Pdf.t -> int list -> Pdf.t
(** [scale_to_fit_pdf input_scale x y op pdf range] scales a page to fit the (** [scale_to_fit_pdf input_scale x y op pdf range] scales a page to fit the
page size given by (x, y) and by the [input_scale] (e.g 1.0 = scale to fit, 0.9 page size given by (x, y) and by the [input_scale] (e.g 1.0 = scale to fit, 0.9
= scale to fit leaving a border etc.). [op] is unused. *) = scale to fit leaving a border etc.). [op] is unused. *)
val scale_to_fit_pdf : ?fast:bool -> float -> float -> float -> 'a -> Pdf.t -> int list -> Pdf.t val scale_to_fit_pdf : ?fast:bool -> float -> (float * float) list -> 'a -> Pdf.t -> int list -> Pdf.t
(** Scale the contents of a page by a given factor centred around a given point in a given range. *) (** Scale the contents of a page by a given factor centred around a given point in a given range. *)
val scale_contents : ?fast:bool -> position -> float -> Pdf.t -> int list -> Pdf.t val scale_contents : ?fast:bool -> position -> float -> Pdf.t -> int list -> Pdf.t

View File

@ -11,6 +11,9 @@ open Pdfio
let initial_file_size = ref 0 let initial_file_size = ref 0
let empty = Pdf.empty ()
let emptypage = Pdfpage.blankpage Pdfpaper.a4
(* Wrap up the file reading functions to exit with code 1 when an encryption (* Wrap up the file reading functions to exit with code 1 when an encryption
problem occurs. This happens when object streams are in an encrypted document problem occurs. This happens when object streams are in an encrypted document
and so it can't be read without the right password... The existing error and so it can't be read without the right password... The existing error
@ -738,8 +741,8 @@ let points_of_papersize p =
let c = Pdfunits.convert 0. unit Pdfunits.PdfPoint in let c = Pdfunits.convert 0. unit Pdfunits.PdfPoint in
c w, c h c w, c h
let firstpage pdf = (*let firstpage pdf =
List.hd (Pdfpage.pages_of_pagetree pdf) List.hd (Pdfpage.pages_of_pagetree pdf)*)
let cropbox pdf page = let cropbox pdf page =
match Pdf.lookup_direct pdf "/CropBox" page.Pdfpage.rest with match Pdf.lookup_direct pdf "/CropBox" page.Pdfpage.rest with
@ -824,100 +827,100 @@ let update_last_number pdf page unt op num = function
in in
h'::t h'::t
let rec parse_units_again pdf page numbers papersize more =
let rec parse_units_again pdf numbers papersize more =
let w, h = points_of_papersize papersize in let w, h = points_of_papersize papersize in
parse_units pdf (h::w::numbers) more parse_units pdf page (h::w::numbers) more
and parse_units pdf numbers = function and parse_units pdf page numbers = function
| Pdfgenlex.LexName "a10portrait"::more -> | Pdfgenlex.LexName "a10portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a10 more parse_units_again pdf page numbers Pdfpaper.a10 more
| Pdfgenlex.LexName "a9portrait"::more -> | Pdfgenlex.LexName "a9portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a9 more parse_units_again pdf page numbers Pdfpaper.a9 more
| Pdfgenlex.LexName "a8portrait"::more -> | Pdfgenlex.LexName "a8portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a8 more parse_units_again pdf page numbers Pdfpaper.a8 more
| Pdfgenlex.LexName "a7portrait"::more -> | Pdfgenlex.LexName "a7portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a7 more parse_units_again pdf page numbers Pdfpaper.a7 more
| Pdfgenlex.LexName "a6portrait"::more -> | Pdfgenlex.LexName "a6portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a6 more parse_units_again pdf page numbers Pdfpaper.a6 more
| Pdfgenlex.LexName "a5portrait"::more -> | Pdfgenlex.LexName "a5portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a5 more parse_units_again pdf page numbers Pdfpaper.a5 more
| Pdfgenlex.LexName "a4portrait"::more -> | Pdfgenlex.LexName "a4portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a4 more parse_units_again pdf page numbers Pdfpaper.a4 more
| Pdfgenlex.LexName "a3portrait"::more -> | Pdfgenlex.LexName "a3portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a3 more parse_units_again pdf page numbers Pdfpaper.a3 more
| Pdfgenlex.LexName "a2portrait"::more -> | Pdfgenlex.LexName "a2portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a2 more parse_units_again pdf page numbers Pdfpaper.a2 more
| Pdfgenlex.LexName "a1portrait"::more -> | Pdfgenlex.LexName "a1portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a1 more parse_units_again pdf page numbers Pdfpaper.a1 more
| Pdfgenlex.LexName "a0portrait"::more -> | Pdfgenlex.LexName "a0portrait"::more ->
parse_units_again pdf numbers Pdfpaper.a0 more parse_units_again pdf page numbers Pdfpaper.a0 more
| Pdfgenlex.LexName "a10landscape"::more -> | Pdfgenlex.LexName "a10landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a10) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a10) more
| Pdfgenlex.LexName "a9landscape"::more -> | Pdfgenlex.LexName "a9landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a9) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a9) more
| Pdfgenlex.LexName "a8landscape"::more -> | Pdfgenlex.LexName "a8landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a8) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a8) more
| Pdfgenlex.LexName "a7landscape"::more -> | Pdfgenlex.LexName "a7landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a7) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a7) more
| Pdfgenlex.LexName "a6landscape"::more -> | Pdfgenlex.LexName "a6landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a6) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a6) more
| Pdfgenlex.LexName "a5landscape"::more -> | Pdfgenlex.LexName "a5landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a5) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a5) more
| Pdfgenlex.LexName "a4landscape"::more -> | Pdfgenlex.LexName "a4landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a4) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a4) more
| Pdfgenlex.LexName "a3landscape"::more -> | Pdfgenlex.LexName "a3landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a3) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a3) more
| Pdfgenlex.LexName "a2landscape"::more -> | Pdfgenlex.LexName "a2landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a2) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a2) more
| Pdfgenlex.LexName "a1landscape"::more -> | Pdfgenlex.LexName "a1landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a1) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a1) more
| Pdfgenlex.LexName "a0landscape"::more -> | Pdfgenlex.LexName "a0landscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.a0) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.a0) more
| Pdfgenlex.LexName "uslegalportrait"::more -> | Pdfgenlex.LexName "uslegalportrait"::more ->
parse_units_again pdf numbers Pdfpaper.uslegal more parse_units_again pdf page numbers Pdfpaper.uslegal more
| Pdfgenlex.LexName "usletterportrait"::more -> | Pdfgenlex.LexName "usletterportrait"::more ->
parse_units_again pdf numbers Pdfpaper.usletter more parse_units_again pdf page numbers Pdfpaper.usletter more
| Pdfgenlex.LexName "uslegallandscape"::more -> | Pdfgenlex.LexName "uslegallandscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.uslegal) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.uslegal) more
| Pdfgenlex.LexName "usletterlandscape"::more -> | Pdfgenlex.LexName "usletterlandscape"::more ->
parse_units_again pdf numbers (Pdfpaper.landscape Pdfpaper.usletter) more parse_units_again pdf page numbers (Pdfpaper.landscape Pdfpaper.usletter) more
| Pdfgenlex.LexInt x::Pdfgenlex.LexName "mm"::more -> | Pdfgenlex.LexInt x::Pdfgenlex.LexName "mm"::more ->
parse_units pdf ((mm <| float_of_int x)::numbers) more parse_units pdf page ((mm <| float_of_int x)::numbers) more
| Pdfgenlex.LexReal x::Pdfgenlex.LexName "mm"::more -> | Pdfgenlex.LexReal x::Pdfgenlex.LexName "mm"::more ->
parse_units pdf (mm x::numbers) more parse_units pdf page (mm x::numbers) more
| Pdfgenlex.LexInt x::Pdfgenlex.LexName "cm"::more -> | Pdfgenlex.LexInt x::Pdfgenlex.LexName "cm"::more ->
parse_units pdf ((cm <| float_of_int x)::numbers) more parse_units pdf page ((cm <| float_of_int x)::numbers) more
| Pdfgenlex.LexReal x::Pdfgenlex.LexName "cm"::more -> | Pdfgenlex.LexReal x::Pdfgenlex.LexName "cm"::more ->
parse_units pdf (cm x::numbers) more parse_units pdf page (cm x::numbers) more
| Pdfgenlex.LexInt x::Pdfgenlex.LexName "in"::more -> | Pdfgenlex.LexInt x::Pdfgenlex.LexName "in"::more ->
parse_units pdf ((inch <| float_of_int x)::numbers) more parse_units pdf page ((inch <| float_of_int x)::numbers) more
| Pdfgenlex.LexReal x::Pdfgenlex.LexName "in"::more -> | Pdfgenlex.LexReal x::Pdfgenlex.LexName "in"::more ->
parse_units pdf (inch x::numbers) more parse_units pdf page (inch x::numbers) more
| Pdfgenlex.LexInt x::more -> | Pdfgenlex.LexInt x::more ->
parse_units pdf (float_of_int x::numbers) more parse_units pdf page (float_of_int x::numbers) more
| Pdfgenlex.LexReal x::more -> | Pdfgenlex.LexReal x::more ->
parse_units pdf (x::numbers) more parse_units pdf page (x::numbers) more
| Pdfgenlex.LexName "pt"::more -> | Pdfgenlex.LexName "pt"::more ->
parse_units pdf numbers more parse_units pdf page numbers more
| Pdfgenlex.LexName | Pdfgenlex.LexName
( "PW" | "PH" | "CW" | "CH" | "PMINX" | "PMINY" | "PMAXX" | "PMAXY" ( "PW" | "PH" | "CW" | "CH" | "PMINX" | "PMINY" | "PMAXX" | "PMAXY"
| "CMINX" | "CMINY" | "CMAXX" | "CMAXY") as page_characteristic::more -> | "CMINX" | "CMINY" | "CMAXX" | "CMAXY") as page_characteristic::more ->
parse_units parse_units
pdf pdf
((find_page_characteristic pdf (firstpage pdf) page_characteristic)::numbers) page
((find_page_characteristic pdf page page_characteristic)::numbers)
more more
| Pdfgenlex.LexName ("add" | "sub" | "mul" | "div") as op:: | Pdfgenlex.LexName ("add" | "sub" | "mul" | "div") as op::
((Pdfgenlex.LexInt _ | Pdfgenlex.LexReal _ | Pdfgenlex.LexName ((Pdfgenlex.LexInt _ | Pdfgenlex.LexReal _ | Pdfgenlex.LexName
( "PW" | "PH" | "CW" | "CH" | "PMINX" | "PMINY" | "PMAXX" | "PMAXY" ( "PW" | "PH" | "CW" | "CH" | "PMINX" | "PMINY" | "PMAXX" | "PMAXY"
| "CMINX" | "CMINY" | "CMAXX" | "CMAXY")) as num):: | "CMINX" | "CMINY" | "CMAXX" | "CMAXY")) as num)::
(Pdfgenlex.LexName ("pt" | "mm" | "cm" | "in") as unt)::more -> (Pdfgenlex.LexName ("pt" | "mm" | "cm" | "in") as unt)::more ->
parse_units pdf (update_last_number pdf (firstpage pdf) unt op num numbers) more parse_units pdf page (update_last_number pdf page unt op num numbers) more
| Pdfgenlex.LexName ("add" | "sub" | "mul" | "div") as op:: | Pdfgenlex.LexName ("add" | "sub" | "mul" | "div") as op::
((Pdfgenlex.LexInt _ | Pdfgenlex.LexReal _ | Pdfgenlex.LexName ((Pdfgenlex.LexInt _ | Pdfgenlex.LexReal _ | Pdfgenlex.LexName
( "PW" | "PH" | "CW" | "CH" | "PMINX" | "PMINY" | "PMAXX" | "PMAXY" ( "PW" | "PH" | "CW" | "CH" | "PMINX" | "PMINY" | "PMAXX" | "PMAXY"
| "CMINX" | "CMINY" | "CMAXX" | "CMAXY")) as num)::more -> | "CMINX" | "CMINY" | "CMAXX" | "CMAXY")) as num)::more ->
parse_units pdf (update_last_number pdf (firstpage pdf) (Pdfgenlex.LexName "pt") op num numbers) more parse_units pdf page (update_last_number pdf page (Pdfgenlex.LexName "pt") op num numbers) more
| _ -> rev numbers | _ -> rev numbers
let rec space_units_inner = function let rec space_units_inner = function
@ -931,33 +934,56 @@ let rec space_units_inner = function
let space_units s = let space_units s =
implode (space_units_inner (explode s)) implode (space_units_inner (explode s))
let parse_units_string pdf s = let parse_units_string pdf page s =
(*Printf.printf "Parsing string [%s]\n" s;*) Printf.printf "Parsing string [%s]\n" s;
let fs = parse_units pdf [] (Pdfgenlex.lex_string <| space_units s) in let fs = parse_units pdf page [] (Pdfgenlex.lex_string <| space_units s) in
(*Printf.printf "Got numbers: %s\n" Printf.printf "Got numbers: %s\n"
(List.fold_left (fun x y -> x ^ " " ^ y) "" (List.map string_of_float (List.fold_left (fun x y -> x ^ " " ^ y) "" (List.map string_of_float fs));
fs));*)
fs fs
let parse_rectangle pdf s = let parse_rectangle pdf s =
try try
match parse_units_string pdf s with match parse_units_string pdf emptypage s with
| [x; y; w; h] -> x, y, w, h | [x; y; w; h] -> x, y, w, h
| _ -> error "Bad rectangle specification" | _ -> error "Bad rectangle specification"
with with
_ -> error "Bad rectangle specification" _ -> error "Bad rectangle specification"
let parse_rectangles pdf s =
try
let pages = Pdfpage.pages_of_pagetree pdf in
let groups = List.map (fun page -> parse_units_string pdf page s) pages in
List.map
(function
| [x; y; w; h] -> (x, y, w, h)
| _ -> error "Bad rectangle specification")
groups
with
_ -> error "Bad rectangle specification"
let parse_coordinate pdf s = let parse_coordinate pdf s =
try try
match parse_units_string pdf s with match parse_units_string pdf emptypage s with
| [dx; dy] -> dx, dy | [dx; dy] -> dx, dy
| _ -> error "Bad coordinate specification" | _ -> error "Bad coordinate specification"
with with
_ -> error "Bad coordinate specification" _ -> error "Bad coordinate specification"
let parse_coordinates pdf s =
try
let pages = Pdfpage.pages_of_pagetree pdf in
let groups = List.map (fun page -> parse_units_string pdf page s) pages in
List.map
(function
| [dx; dy] -> (dx, dy)
| _ -> error "Bad coordinate specification")
groups
with
_ -> error "Bad coordinate specification"
let parse_single_number pdf s = let parse_single_number pdf s =
try try
match parse_units_string pdf s with match parse_units_string pdf emptypage s with
| [x] -> x | [x] -> x
| _ -> error "Bad number Argument" | _ -> error "Bad number Argument"
with with
@ -1026,7 +1052,7 @@ let displaydoctitle b =
try setop (DisplayDocTitle (bool_of_string b)) () with try setop (DisplayDocTitle (bool_of_string b)) () with
_ -> failwith "DisplayDocTitle: must use true or false" _ -> failwith "DisplayDocTitle: must use true or false"
let empty = Pdf.empty ()
let setsplitbookmarks i = setop (SplitOnBookmarks i) () let setsplitbookmarks i = setop (SplitOnBookmarks i) ()
let setstdout () = args.out <- Stdout let setstdout () = args.out <- Stdout
@ -3252,20 +3278,19 @@ let go () =
begin match args.inputs, args.out with begin match args.inputs, args.out with
| (_, pagespec, _, _, _, _)::_, _ -> | (_, pagespec, _, _, _, _)::_, _ ->
let pdf = get_single_pdf (Some Crop) false in let pdf = get_single_pdf (Some Crop) false in
let x, y, w, h = parse_rectangle pdf args.rectangle in let xywhlist = parse_rectangles pdf args.rectangle in
let range = parse_pagespec pdf pagespec in let range = parse_pagespec pdf pagespec in
let pdf = Cpdf.crop_pdf x y w h pdf range in let pdf = Cpdf.crop_pdf xywhlist pdf range in
write_pdf false pdf write_pdf false pdf
| _ -> error "crop: bad command line" | _ -> error "crop: bad command line"
end end
| Some MediaBox -> | Some MediaBox ->
begin match args.inputs, args.out with begin match args.inputs, args.out with
| (_, pagespec, _, _, _, _)::_, _ -> | (_, pagespec, _, _, _, _)::_, _ ->
let pdf = get_single_pdf (Some MediaBox) false in let pdf = get_single_pdf (Some MediaBox) false in
let x, y, w, h = parse_rectangle pdf args.rectangle in let xywhlist = parse_rectangles pdf args.rectangle in
let range = parse_pagespec pdf pagespec in let range = parse_pagespec pdf pagespec in
let pdf = Cpdf.set_mediabox x y w h pdf range in let pdf = Cpdf.set_mediabox xywhlist pdf range in
write_pdf false pdf write_pdf false pdf
| _ -> error "set media box: bad command line" | _ -> error "set media box: bad command line"
end end
@ -3554,21 +3579,19 @@ let go () =
| Some Shift -> | Some Shift ->
let pdf = get_single_pdf args.op false in let pdf = get_single_pdf args.op false in
let range = parse_pagespec pdf (get_pagespec ()) in let range = parse_pagespec pdf (get_pagespec ()) in
begin match parse_coordinate pdf args.coord with (dx, dy) -> let dxdylist = parse_coordinates pdf args.coord in
write_pdf false (Cpdf.shift_pdf ~fast:args.fast dx dy pdf range) write_pdf false (Cpdf.shift_pdf ~fast:args.fast dxdylist pdf range)
end
| Some Scale -> | Some Scale ->
let pdf = get_single_pdf args.op false in let pdf = get_single_pdf args.op false in
let range = parse_pagespec pdf (get_pagespec ()) in let range = parse_pagespec pdf (get_pagespec ()) in
begin match parse_coordinate pdf args.coord with (sx, sy) -> let sxsylist = parse_coordinates pdf args.coord in
write_pdf false (Cpdf.scale_pdf ~fast:args.fast sx sy pdf range) write_pdf false (Cpdf.scale_pdf ~fast:args.fast sxsylist pdf range)
end
| Some ScaleToFit -> | Some ScaleToFit ->
let pdf = get_single_pdf args.op false in let pdf = get_single_pdf args.op false in
let range = parse_pagespec pdf (get_pagespec ()) in let range = parse_pagespec pdf (get_pagespec ()) in
let x, y = parse_coordinate pdf args.coord let xylist = parse_coordinates pdf args.coord
and scale = args.scale in and scale = args.scale in
write_pdf false (Cpdf.scale_to_fit_pdf ~fast:args.fast scale x y args.op pdf range) write_pdf false (Cpdf.scale_to_fit_pdf ~fast:args.fast scale xylist args.op pdf range)
| Some (ScaleContents scale) -> | Some (ScaleContents scale) ->
let pdf = get_single_pdf args.op false in let pdf = get_single_pdf args.op false in
let range = parse_pagespec pdf (get_pagespec ()) in let range = parse_pagespec pdf (get_pagespec ()) in