acrobat 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.standard.yml +3 -0
- data/CHANGELOG.md +5 -0
- data/CODE_OF_CONDUCT.md +132 -0
- data/Guardfile +28 -30
- data/{LICENSE.adoc → LICENSE.txt} +3 -4
- data/README.md +107 -0
- data/Rakefile +6 -54
- data/examples/6030.17.antenna.pdf +0 -0
- data/examples/6030.17.cm300.tx.pdf +0 -0
- data/examples/form_field.rb +21 -0
- data/examples/merge.rb +11 -0
- data/lib/acrobat/app.rb +172 -187
- data/lib/acrobat/jso.rb +87 -94
- data/lib/acrobat/pdoc.rb +134 -137
- data/lib/acrobat/version.rb +5 -0
- data/lib/acrobat.rb +45 -48
- data/samples_other/background.js +40 -0
- data/samples_other/find_word.vb +440 -0
- data/samples_other/form.vb +393 -0
- data/vba/overlay.vba +40 -0
- metadata +27 -190
- data/.gitignore +0 -32
- data/History.adoc +0 -6
- data/Manifest.txt +0 -14
- data/README.adoc +0 -117
- data/bin/acrobat +0 -3
- data/test/acrobat_test.rb +0 -36
- data/test/test_helper.rb +0 -13
data/lib/acrobat/app.rb
CHANGED
@@ -1,187 +1,172 @@
|
|
1
|
-
require
|
2
|
-
|
3
|
-
require_relative
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
end
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
#
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
@ole_obj
|
40
|
-
@docs = []
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
#
|
45
|
-
#
|
46
|
-
#
|
47
|
-
#
|
48
|
-
#
|
49
|
-
# doc
|
50
|
-
# doc.
|
51
|
-
#
|
52
|
-
#
|
53
|
-
#
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
#
|
77
|
-
# @
|
78
|
-
#
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
#
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
#
|
129
|
-
#
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
|
163
|
-
|
164
|
-
|
165
|
-
|
166
|
-
|
167
|
-
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
def form
|
176
|
-
Form.new(self,WIN32OLE.new("AFormAut.App"))
|
177
|
-
end
|
178
|
-
|
179
|
-
private
|
180
|
-
|
181
|
-
def load_constants(ole_obj)
|
182
|
-
WIN32OLE.const_load(ole_obj, ACRO) unless ACRO.constants.size > 0
|
183
|
-
end
|
184
|
-
|
185
|
-
end
|
186
|
-
|
187
|
-
end
|
1
|
+
require "win32ole"
|
2
|
+
require_relative "pdoc"
|
3
|
+
require_relative "jso"
|
4
|
+
|
5
|
+
module Acrobat
|
6
|
+
class FileNotFound < StandardError
|
7
|
+
def initialize(path)
|
8
|
+
super("File not found: #{path}")
|
9
|
+
end
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
module FileSystemObject
|
14
|
+
@instance = nil
|
15
|
+
def self.instance
|
16
|
+
@instance ||= WIN32OLE.new("Scripting.FileSystemObject")
|
17
|
+
@instance
|
18
|
+
end
|
19
|
+
|
20
|
+
def self.windows_path(path)
|
21
|
+
FileSystemObject.instance.GetAbsolutePathname(path.to_s)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
module ACRO; end
|
26
|
+
|
27
|
+
module Acrobat
|
28
|
+
class App
|
29
|
+
# [WIN32_OLE] ole_obj
|
30
|
+
attr_reader :ole_obj
|
31
|
+
|
32
|
+
# the wrapped [PDoc] PDoc object
|
33
|
+
attr_reader :pdoc
|
34
|
+
|
35
|
+
# Initialize the
|
36
|
+
# @return [App] return an instance of App
|
37
|
+
def initialize
|
38
|
+
@ole_obj = WIN32OLE.new("AcroExch.App")
|
39
|
+
load_constants(@ole_obj)
|
40
|
+
@docs = []
|
41
|
+
end
|
42
|
+
|
43
|
+
# Runs the adobe app and quits at the end
|
44
|
+
# @yield app [App]
|
45
|
+
#
|
46
|
+
# @example
|
47
|
+
# Acrobat::App.run do |app|
|
48
|
+
# doc = app.open('doc.pdf')
|
49
|
+
# doc.fill_form( city: 'City', state: 'ST')
|
50
|
+
# doc.save_as('filled.pdf')
|
51
|
+
# end
|
52
|
+
#
|
53
|
+
# @return nil
|
54
|
+
def self.run
|
55
|
+
the_app = new
|
56
|
+
yield the_app
|
57
|
+
ensure
|
58
|
+
the_app&.quit
|
59
|
+
GC.start
|
60
|
+
nil
|
61
|
+
end
|
62
|
+
|
63
|
+
def self.replace_pages(src, replacement, output_name:, **opts)
|
64
|
+
run do |app|
|
65
|
+
app.open(src) do |doc|
|
66
|
+
doc.replace_pages(replacement, **opts)
|
67
|
+
doc.save_as(output_name)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
# Fills the form with updates in a hash
|
73
|
+
# @example
|
74
|
+
# Acrobat::App.fill_form(myform.pdf, output_name: 'filled.pdf
|
75
|
+
# , update_hash: { name: 'dom', filled_date: 1/20/2013
|
76
|
+
# @param doc [String] the String path of a fillable pdf file
|
77
|
+
# @param output_name [String] the name of the saved filled pdf file
|
78
|
+
# @param update_hash [Hash] the hash with updates
|
79
|
+
def self.fill_form(form, output_name:, update_hash:)
|
80
|
+
run do |app|
|
81
|
+
doc = app.open(form)
|
82
|
+
doc.fill_form(update_hash)
|
83
|
+
doc.save_as(output_name)
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
87
|
+
# show the Adobe Acrobat application
|
88
|
+
def show
|
89
|
+
ole_obj.Show
|
90
|
+
end
|
91
|
+
|
92
|
+
# hide the Adobe Acrobat application
|
93
|
+
def hide
|
94
|
+
ole_obj.Hide
|
95
|
+
end
|
96
|
+
|
97
|
+
# Finds the pdfs in a dir
|
98
|
+
# @param dir [String] the directory to find pdfs in
|
99
|
+
# @return [Array] of pdf files
|
100
|
+
def find_pdfs_in_dir(dir)
|
101
|
+
Pathname.glob(dir + "/*.pdf")
|
102
|
+
end
|
103
|
+
|
104
|
+
def merge_pdfs(*pdfs)
|
105
|
+
pdf_array = Array(pdfs).flatten
|
106
|
+
raise "Not enough pdfs to merge" if pdf_array.size < 2
|
107
|
+
first, *rest = pdf_array
|
108
|
+
doc = self.open(first)
|
109
|
+
rest.each do |path|
|
110
|
+
doc.merge(path)
|
111
|
+
end
|
112
|
+
doc
|
113
|
+
end
|
114
|
+
|
115
|
+
# merges the pdfs in directory
|
116
|
+
# @param dir [String] the path of the directory
|
117
|
+
# @param name [String,Nil] the name of the returned pdf file
|
118
|
+
# if the name is nil, the name is "merged.pdf"
|
119
|
+
# @param output_dir [String,Nil] the name of the output dir
|
120
|
+
# if the output_dir is nil, the output dir is the dir param
|
121
|
+
# return [Boolean] if the merge was successful or not
|
122
|
+
def merge_pdfs_in_dir(dir, name: nil, output_dir: nil)
|
123
|
+
name || "merged.pdf"
|
124
|
+
dir = output_dir || dir
|
125
|
+
merge_pdfs(find_pdfs_in_dir(dir))
|
126
|
+
end
|
127
|
+
|
128
|
+
# quit the Adobe App.
|
129
|
+
# closes the open adobe documents and quits the program
|
130
|
+
# @return nil
|
131
|
+
def quit
|
132
|
+
begin
|
133
|
+
docs.each { |d| d.close }
|
134
|
+
ole_obj.Exit
|
135
|
+
rescue
|
136
|
+
return nil
|
137
|
+
end
|
138
|
+
nil
|
139
|
+
end
|
140
|
+
|
141
|
+
attr_reader :docs
|
142
|
+
|
143
|
+
# open the file.
|
144
|
+
# @param file [String #to_path]
|
145
|
+
# @return [PDoc] the open file as a Pdoc instance
|
146
|
+
def open(file)
|
147
|
+
filepath = Pathname(file).expand_path
|
148
|
+
raise FileNotFound.new(filepath) unless filepath.file?
|
149
|
+
pdoc = WIN32OLE.new("AcroExch.PDDoc")
|
150
|
+
is_opened = pdoc.open FileSystemObject.windows_path(filepath)
|
151
|
+
doc = PDoc.new(self, pdoc, filepath) if is_opened
|
152
|
+
docs << doc if is_opened
|
153
|
+
return doc unless block_given?
|
154
|
+
begin
|
155
|
+
yield doc
|
156
|
+
ensure
|
157
|
+
doc.close
|
158
|
+
nil
|
159
|
+
end
|
160
|
+
end
|
161
|
+
|
162
|
+
def form
|
163
|
+
Form.new(self, WIN32OLE.new("AFormAut.App"))
|
164
|
+
end
|
165
|
+
|
166
|
+
private
|
167
|
+
|
168
|
+
def load_constants(ole_obj)
|
169
|
+
WIN32OLE.const_load(ole_obj, ACRO) unless ACRO.constants.size > 0
|
170
|
+
end
|
171
|
+
end
|
172
|
+
end
|
data/lib/acrobat/jso.rb
CHANGED
@@ -1,94 +1,87 @@
|
|
1
|
-
module Acrobat
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
when
|
15
|
-
ole_get_field(name_or_number
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
end
|
71
|
-
|
72
|
-
def
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
set_field(k,v)
|
89
|
-
end
|
90
|
-
end
|
91
|
-
|
92
|
-
end
|
93
|
-
|
94
|
-
end
|
1
|
+
module Acrobat
|
2
|
+
class Jso
|
3
|
+
attr_reader :doc, :ole_obj
|
4
|
+
|
5
|
+
def initialize(doc, ole)
|
6
|
+
@doc = doc
|
7
|
+
@ole_obj = ole
|
8
|
+
end
|
9
|
+
|
10
|
+
def find_field(name_or_number)
|
11
|
+
case name_or_number
|
12
|
+
when String, Symbol
|
13
|
+
ole_get_field(name_or_number.to_s)
|
14
|
+
when Number
|
15
|
+
ole_get_field(name_or_number)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
def ole_get_field(field)
|
20
|
+
ole_obj.getField(field)
|
21
|
+
end
|
22
|
+
|
23
|
+
def console
|
24
|
+
@console ||= ole_obj.console
|
25
|
+
end
|
26
|
+
|
27
|
+
def show_console
|
28
|
+
console.show
|
29
|
+
end
|
30
|
+
|
31
|
+
def field_names
|
32
|
+
result = []
|
33
|
+
count = field_count
|
34
|
+
0.upto(count - 1) do |i|
|
35
|
+
result << ole_obj.getNthFieldName(i)
|
36
|
+
end
|
37
|
+
result
|
38
|
+
end
|
39
|
+
|
40
|
+
def export_as_fdf(name)
|
41
|
+
end
|
42
|
+
|
43
|
+
def import_fdf(path)
|
44
|
+
end
|
45
|
+
|
46
|
+
def fields_hash
|
47
|
+
result = {}
|
48
|
+
field_names.each_with_object(result) do |name, h|
|
49
|
+
h[name] = get_field(name)
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
|
54
|
+
# // Enumerate through all of the fields in the document.
|
55
|
+
# for (var i = 0; i < this.numFields; i++)
|
56
|
+
# console.println("Field[" + i + "] = " + this.getNthFieldName(i));
|
57
|
+
|
58
|
+
def set_field(name, value)
|
59
|
+
field = find_field(name)
|
60
|
+
field.Value = value.to_s if field
|
61
|
+
rescue
|
62
|
+
require "pry"
|
63
|
+
binding.pry
|
64
|
+
nil
|
65
|
+
end
|
66
|
+
|
67
|
+
def get_field(name)
|
68
|
+
field = find_field(name)
|
69
|
+
field&.Value
|
70
|
+
end
|
71
|
+
|
72
|
+
def field_count
|
73
|
+
ole_obj.numFields.to_int
|
74
|
+
end
|
75
|
+
|
76
|
+
def clear_form
|
77
|
+
ole_obj.resetForm
|
78
|
+
end
|
79
|
+
|
80
|
+
def fill_form(hash)
|
81
|
+
clear_form
|
82
|
+
hash.each do |k, v|
|
83
|
+
set_field(k, v)
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|