A single or batch, interactive or drag & drop application that will process multiple files/folders, and export PDF from Pages v5. PDF documents are written to the original Pages document location. The application will notify when done with a total processed count, and writes a report to the desktop containing a time stamp, pdf quality, and path to each PDF. It also adds a Finder comment field to each PDF with the PDF quality for Spotlight/Finder searches (e.g. comment: Best, comment: Default, etc.).
There are several hours of debugging in this large script, as it is doing far more than just the basic exporting of PDF documents. This does not hinder its performance, as the bottleneck will be the size of your Pages documents, and the time it takes Pages to process each one. Any dialog box that Pages v5 throws during processing will probably hang the script. 😉
Tested with Pages v5.6.1 on OS X 10.11.3. Requires Pages v5 or later, though only tested with v5.6.1.
Installation:
- Copy and paste the following code into your AppleScript Editor (Launchpad : Other : Script Editor).
- Click the hammer icon on the toolbar to compile it. There are no errors on this end.
- File menu : Save… (You are saving the script source here)
- Save As: p5_pdf
- Save location: (e.g. Documents/Scripts) this is arbitrary, but put it where you don’t accidentally delete it.
- Tags: blank
- File Format: Select Text (adds .applescript to the above filename)
- No boxes checked
- Save
- File menu : option key: Save As… (you are making the Desktop application)
- Save As: p5_pdf
- Save location: Desktop
- Tags: blank
- File Format: Application (adds .app to the above filename)
- √ Hide extension
- No other boxes checked
- Save
- This script is not compatible with the Run AppleScript action in Automator. You can build the Automator application, but drag and drop will invoke the File Chooser when you don’t want it.
Usage:
As a bi-modal application, you can double-click to interactively choose your files and folders, or just drag & drop files and folders on the application icon.
Code:
-- Pages5_PDF.applescript
-- Both interactive (double-click), and drag & drop application. Batch export Pages to PDF.
-- If Pages v5.6 or later, will either prompt for PDF Quality, or if drag & drop,
-- use PDF quality Best. PDF are written to original location of Pages document.
-- Requires Pages v5 or later. Tested on OS X 10.11.3 with Pages v5.6.1.
-- Version 1.6, VikingOSX, Mar 8, 2016, Apple Support Communities
property default_path : ((path to desktop) as text)
property pdf_list : {"Best", "Better", "Good"}
property report_file : ((path to desktop as text) & "PDFExport.txt")
property exported_files : {}
property fileCnt : 0 as integer
-- Pages v5.6 or later, and drag & drop used
property pdf_quality : "Best"
property pages_version : missing value
property Pages5 : false as boolean
-- Interactive section: access with double-click of application
on run
-- can only run this with Pages v5 or later
set {pages_version, Pages5} to is_pages5()
if not Pages5 then
set pages_version to missing value
return
end if
try
set fileObjects to {}
set returnObjects to open_files_folders(default_path)
if returnObjects contains "None" then
error number -128
else if returnObjects is equal to POSIX path of (text 1 thru -2 of default_path) then
tell application "Finder"
display alert ¬
"Actually select something. Don't just click Select." as critical giving up after 10
end tell
return
end if
-- build alias file list from file and folder selection
repeat with i from 1 to (number of paragraphs of returnObjects)
set theFile to (paragraph i of returnObjects) as POSIX file as alias
copy theFile to the end of fileObjects
end repeat
-- commencing with Pages v5.6, one can set PDF Export quality
if pages_version ≥ "5.6" then
tell application "Finder"
set pdf_quality to (choose from listpdf_list ¬
with prompt "PDF Export Quality" default items {"Best"}) as text
end tell
end if
-- handle user cancel
if pdf_quality is equal to false then
set pdf_quality to "Best"
error number -128
end if
-- Pass file and folder selection on to the drag & drop handler
openfileObjects
on error errmsg number errnbr
error_handler(errnbr, errmsg)
set pages_version to missing value
end try
return
end run
-- drag & drop section
on openfileObjects
-- skip if already performed interactively
if not Pages5 then
set {pages_version, Pages5} to is_pages5()
if not Pages5 then
set pages_version to missing value
return
end if
end if
set pages_list to {}
repeat with i from 1 to the (count of items of fileObjects)
set afile to (item i of fileObjects) as alias
tell application "Finder" to set akind to kind of afile
if akind contains "Folder" then
tell application "Finder"
set pages_list to (every item in entire contents of folder afile whose kind is "Pages Publication") as alias list
end tell
repeat with pages_file from 1 to (count of items of pages_list)
export_file(itempages_file of pages_list)
end repeat
else if akind contains "Pages Publication" then
export_file(afile)
end if
end repeat
if fileCnt > 0 as integer then
display notification "Files exported to PDF: " & (fileCnt as text) ¬
with title "Pages v5 File Export Facility" subtitle "Processing Complete"
set fileCnt to 0 as integer
end if
-- ensure that Pages quits when done
-- tell application "Pages" to if it is running then quit
set pdf_quality to "Best"
return
end open
on is_pages5()
set status to false as boolean
tell application "Pages" to set its_version to version of it
if its_version ≥ "5.0" then
set status to true as boolean
else
-- Don't leave Pages '09 running
tell application "Pages" to if it is running then quit
tell application "Finder"
display alert ¬
"Pages v5 or later is required for this script. Program exiting" as critical giving up after 10
end tell
end if
return {its_version, status}
end is_pages5
on export_file(theFile)
if (theFile as text) does not end with ":" then
-- single file format
set exportDocument to text 1 thru -6 of (theFile as text) & "pdf"
else
-- package folder, so trim trailing HFS ":" in filename
set exportDocument to text 1 thru -7 of (theFile as text) & "pdf"
end if
tell application "Pages"
if pages_version ≥ "5.6" then
if pdf_quality is "Best" then
set export_quality to (Best as constant)
else if pdf_quality is "Better" then
set export_quality to (Better as constant)
else if pdf_quality is "Good" then
set export_quality to (Good as constant)
end if
set finder_comment to "Quality - " & pdf_quality
else
set finder_comment to "Quality - Default"
end if
try
with timeout of 1200 seconds
set mydoc to open theFile
delay 1
if pages_version ≥ "5.6" then
exportmydoctofileexportDocumentasPDF ¬
with properties {image quality:export_quality}
else
exportmydoctofileexportDocumentasPDF
end if
end timeout
closemydocsavingno
set fileCnt to (fileCnt + 1) as integer
-- Build nested list of exported PDF information for reporting
-- get 24 hr stamp as YYYY-MM-DD HH:MM (see man strftime)
set timestamp to (do shell script "date +\"%F %R\"") as text
set exported_files to exported_files & {{timestamp, pdf_quality, exportDocument}}
-- {{'2016-03-08 11:26', 'Best', 'filename'}, {second item}, ... {n item}}
on error errmsg number errnbr
error_handler(errnbr, errmsg)
set fileCnt to 0 as integer
set pdf_quality to "Best"
tell application "Pages" to if it is running then quit
end try
end tell
-- Force file extension display
-- Put export quality as Finder comment on PDF
-- Spotlight/Finder search as comment:Best
tell application "Finder"
set extension hidden of (file exportDocument as alias) to false
set comment of (fileexportDocument as alias) to finder_comment
end tell
-- timestamped log of exported PDF files in this format
-- 2016-03-08 Best /Users/yourname/Desktop/test.pdf
-- log (exported_files)
log_report(exported_files)
return
end export_file
on log_report(L2list)
-- pass in a list of lists and extract content into export report file
set space2 to space & space
try
set fRef to (open for accessfilereport_file with write permission)
-- if the report file does not exist, create a new one with heading
if (get eof fRef) = 0 then
write "PDF Export Log" & return to fRef starting at eof
end if
-- otherwise, append timestamp, quality, and file path to the report
repeat with i from 1 to count of L2list
set T to first item of (item i of L2list) as text -- get timestamp
set Q to second item of (item i of L2list) -- get PDF quality
set F to POSIX path of (third item of (item i of L2list)) as text -- get PDF filename
set output to T & space2 & Q & space2 & F & return
writeoutputtofRefastextstarting ateof
end repeat
close accessfRef
set exported_files to {}
on error errmsg number errnbr
error_handler(errnbr, errmsg)
close accessfRef
end try
return
end log_report
on error_handler(nbr, msg)
tell application "Finder"
display alert "[ " & nbr & " ] " & msgascriticalgiving up after 10
end tell
return
end error_handler
on open_files_folders(openfolder)
-- custom NSOpenPanel that pops above all other windows, and offers
-- multiple file and folder selection. Input is filtered to
-- Pages documents and folders. Returns list of selected items, or
-- None if Cancel button pressed.
return do shell script "/usr/bin/python <<'EOF' - " & openfolder & "
#/usr/bin/python
# coding: utf-8
from Foundation import NSURL, YES
from AppKit import NSOpenPanel, NSMakeRect, NSApp, NSOKButton
import os
import sys
def openFile():
fileTypes = ['com.apple.iWork.pages.pages',
'com.apple.iWork.pages.sffpages',
'com.apple.iWork.Pages',
'public.folder',
'public.directory']
theTitle = 'Open Panel'
line1 = 'Select files and folders using the command or shift key.'
line2 = 'Only Pages (.pages) documents will be processed.'
theMsg = '{}\\n{}'.format(line1, line2)
# If command-line open directory is missing, default to Desktop.
if len(sys.argv) == 2:
openfolder = ''.join(os.path.expanduser(sys.argv[1]))
else:
openfolder = ''.join(os.path.expanduser('~/Desktop'))
opanel = NSOpenPanel.openPanel()
# Force to normal size open panel
opanel.setFrame_display_(NSMakeRect(0, 0, 720, 525), YES)
opanel.setTitle_(theTitle)
opanel.setMessage_(theMsg)
opanel.setPrompt_('Select')
opanel.setAllowedFileTypes_(fileTypes)
opanel.setCanCreateDirectories_(False)
opanel.setCanChooseDirectories_(True)
opanel.setCanChooseFiles_(True)
opanel.setTreatsFilePackagesAsDirectories_(False)
opanel.setAllowsMultipleSelection_(True)
opanel.setResolvesAliases_(True)
# opanel.setShowsHiddenFiles_(True)
opanel.setDirectoryURL_(NSURL.fileURLWithPath_isDirectory_(openfolder,
YES))
# Make topmost window on open
NSApp.activateIgnoringOtherApps_(YES)
if opanel.runModal() == NSOKButton:
return opanel.filenames()
else:
return 'None'
def main():
try:
fileret = openFile()
if 'None' not in fileret:
print('\\n'.join(fileret))
else:
print(fileret)
except TypeError:
pass
if __name__ == '__main__':
sys.exit(main())
EOF"
end open_files_folders