diff options
-rw-r--r-- | COPYING | 674 | ||||
-rw-r--r-- | README | 46 | ||||
-rw-r--r-- | exifilm.glade | 552 | ||||
-rw-r--r-- | exifilm.gladep | 8 | ||||
-rw-r--r-- | exifilm.py | 383 | ||||
-rw-r--r-- | lfrecord.ps | 781 | ||||
-rw-r--r-- | lfrecord.py | 863 | ||||
-rw-r--r-- | printrecord.py | 187 |
8 files changed, 3494 insertions, 0 deletions
@@ -0,0 +1,674 @@ | |||
1 | GNU GENERAL PUBLIC LICENSE | ||
2 | Version 3, 29 June 2007 | ||
3 | |||
4 | Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/> | ||
5 | Everyone is permitted to copy and distribute verbatim copies | ||
6 | of this license document, but changing it is not allowed. | ||
7 | |||
8 | Preamble | ||
9 | |||
10 | The GNU General Public License is a free, copyleft license for | ||
11 | software and other kinds of works. | ||
12 | |||
13 | The licenses for most software and other practical works are designed | ||
14 | to take away your freedom to share and change the works. By contrast, | ||
15 | the GNU General Public License is intended to guarantee your freedom to | ||
16 | share and change all versions of a program--to make sure it remains free | ||
17 | software for all its users. We, the Free Software Foundation, use the | ||
18 | GNU General Public License for most of our software; it applies also to | ||
19 | any other work released this way by its authors. You can apply it to | ||
20 | your programs, too. | ||
21 | |||
22 | When we speak of free software, we are referring to freedom, not | ||
23 | price. Our General Public Licenses are designed to make sure that you | ||
24 | have the freedom to distribute copies of free software (and charge for | ||
25 | them if you wish), that you receive source code or can get it if you | ||
26 | want it, that you can change the software or use pieces of it in new | ||
27 | free programs, and that you know you can do these things. | ||
28 | |||
29 | To protect your rights, we need to prevent others from denying you | ||
30 | these rights or asking you to surrender the rights. Therefore, you have | ||
31 | certain responsibilities if you distribute copies of the software, or if | ||
32 | you modify it: responsibilities to respect the freedom of others. | ||
33 | |||
34 | For example, if you distribute copies of such a program, whether | ||
35 | gratis or for a fee, you must pass on to the recipients the same | ||
36 | freedoms that you received. You must make sure that they, too, receive | ||
37 | or can get the source code. And you must show them these terms so they | ||
38 | know their rights. | ||
39 | |||
40 | Developers that use the GNU GPL protect your rights with two steps: | ||
41 | (1) assert copyright on the software, and (2) offer you this License | ||
42 | giving you legal permission to copy, distribute and/or modify it. | ||
43 | |||
44 | For the developers' and authors' protection, the GPL clearly explains | ||
45 | that there is no warranty for this free software. For both users' and | ||
46 | authors' sake, the GPL requires that modified versions be marked as | ||
47 | changed, so that their problems will not be attributed erroneously to | ||
48 | authors of previous versions. | ||
49 | |||
50 | Some devices are designed to deny users access to install or run | ||
51 | modified versions of the software inside them, although the manufacturer | ||
52 | can do so. This is fundamentally incompatible with the aim of | ||
53 | protecting users' freedom to change the software. The systematic | ||
54 | pattern of such abuse occurs in the area of products for individuals to | ||
55 | use, which is precisely where it is most unacceptable. Therefore, we | ||
56 | have designed this version of the GPL to prohibit the practice for those | ||
57 | products. If such problems arise substantially in other domains, we | ||
58 | stand ready to extend this provision to those domains in future versions | ||
59 | of the GPL, as needed to protect the freedom of users. | ||
60 | |||
61 | Finally, every program is threatened constantly by software patents. | ||
62 | States should not allow patents to restrict development and use of | ||
63 | software on general-purpose computers, but in those that do, we wish to | ||
64 | avoid the special danger that patents applied to a free program could | ||
65 | make it effectively proprietary. To prevent this, the GPL assures that | ||
66 | patents cannot be used to render the program non-free. | ||
67 | |||
68 | The precise terms and conditions for copying, distribution and | ||
69 | modification follow. | ||
70 | |||
71 | TERMS AND CONDITIONS | ||
72 | |||
73 | 0. Definitions. | ||
74 | |||
75 | "This License" refers to version 3 of the GNU General Public License. | ||
76 | |||
77 | "Copyright" also means copyright-like laws that apply to other kinds of | ||
78 | works, such as semiconductor masks. | ||
79 | |||
80 | "The Program" refers to any copyrightable work licensed under this | ||
81 | License. Each licensee is addressed as "you". "Licensees" and | ||
82 | "recipients" may be individuals or organizations. | ||
83 | |||
84 | To "modify" a work means to copy from or adapt all or part of the work | ||
85 | in a fashion requiring copyright permission, other than the making of an | ||
86 | exact copy. The resulting work is called a "modified version" of the | ||
87 | earlier work or a work "based on" the earlier work. | ||
88 | |||
89 | A "covered work" means either the unmodified Program or a work based | ||
90 | on the Program. | ||
91 | |||
92 | To "propagate" a work means to do anything with it that, without | ||
93 | permission, would make you directly or secondarily liable for | ||
94 | infringement under applicable copyright law, except executing it on a | ||
95 | computer or modifying a private copy. Propagation includes copying, | ||
96 | distribution (with or without modification), making available to the | ||
97 | public, and in some countries other activities as well. | ||
98 | |||
99 | To "convey" a work means any kind of propagation that enables other | ||
100 | parties to make or receive copies. Mere interaction with a user through | ||
101 | a computer network, with no transfer of a copy, is not conveying. | ||
102 | |||
103 | An interactive user interface displays "Appropriate Legal Notices" | ||
104 | to the extent that it includes a convenient and prominently visible | ||
105 | feature that (1) displays an appropriate copyright notice, and (2) | ||
106 | tells the user that there is no warranty for the work (except to the | ||
107 | extent that warranties are provided), that licensees may convey the | ||
108 | work under this License, and how to view a copy of this License. If | ||
109 | the interface presents a list of user commands or options, such as a | ||
110 | menu, a prominent item in the list meets this criterion. | ||
111 | |||
112 | 1. Source Code. | ||
113 | |||
114 | The "source code" for a work means the preferred form of the work | ||
115 | for making modifications to it. "Object code" means any non-source | ||
116 | form of a work. | ||
117 | |||
118 | A "Standard Interface" means an interface that either is an official | ||
119 | standard defined by a recognized standards body, or, in the case of | ||
120 | interfaces specified for a particular programming language, one that | ||
121 | is widely used among developers working in that language. | ||
122 | |||
123 | The "System Libraries" of an executable work include anything, other | ||
124 | than the work as a whole, that (a) is included in the normal form of | ||
125 | packaging a Major Component, but which is not part of that Major | ||
126 | Component, and (b) serves only to enable use of the work with that | ||
127 | Major Component, or to implement a Standard Interface for which an | ||
128 | implementation is available to the public in source code form. A | ||
129 | "Major Component", in this context, means a major essential component | ||
130 | (kernel, window system, and so on) of the specific operating system | ||
131 | (if any) on which the executable work runs, or a compiler used to | ||
132 | produce the work, or an object code interpreter used to run it. | ||
133 | |||
134 | The "Corresponding Source" for a work in object code form means all | ||
135 | the source code needed to generate, install, and (for an executable | ||
136 | work) run the object code and to modify the work, including scripts to | ||
137 | control those activities. However, it does not include the work's | ||
138 | System Libraries, or general-purpose tools or generally available free | ||
139 | programs which are used unmodified in performing those activities but | ||
140 | which are not part of the work. For example, Corresponding Source | ||
141 | includes interface definition files associated with source files for | ||
142 | the work, and the source code for shared libraries and dynamically | ||
143 | linked subprograms that the work is specifically designed to require, | ||
144 | such as by intimate data communication or control flow between those | ||
145 | subprograms and other parts of the work. | ||
146 | |||
147 | The Corresponding Source need not include anything that users | ||
148 | can regenerate automatically from other parts of the Corresponding | ||
149 | Source. | ||
150 | |||
151 | The Corresponding Source for a work in source code form is that | ||
152 | same work. | ||
153 | |||
154 | 2. Basic Permissions. | ||
155 | |||
156 | All rights granted under this License are granted for the term of | ||
157 | copyright on the Program, and are irrevocable provided the stated | ||
158 | conditions are met. This License explicitly affirms your unlimited | ||
159 | permission to run the unmodified Program. The output from running a | ||
160 | covered work is covered by this License only if the output, given its | ||
161 | content, constitutes a covered work. This License acknowledges your | ||
162 | rights of fair use or other equivalent, as provided by copyright law. | ||
163 | |||
164 | You may make, run and propagate covered works that you do not | ||
165 | convey, without conditions so long as your license otherwise remains | ||
166 | in force. You may convey covered works to others for the sole purpose | ||
167 | of having them make modifications exclusively for you, or provide you | ||
168 | with facilities for running those works, provided that you comply with | ||
169 | the terms of this License in conveying all material for which you do | ||
170 | not control copyright. Those thus making or running the covered works | ||
171 | for you must do so exclusively on your behalf, under your direction | ||
172 | and control, on terms that prohibit them from making any copies of | ||
173 | your copyrighted material outside their relationship with you. | ||
174 | |||
175 | Conveying under any other circumstances is permitted solely under | ||
176 | the conditions stated below. Sublicensing is not allowed; section 10 | ||
177 | makes it unnecessary. | ||
178 | |||
179 | 3. Protecting Users' Legal Rights From Anti-Circumvention Law. | ||
180 | |||
181 | No covered work shall be deemed part of an effective technological | ||
182 | measure under any applicable law fulfilling obligations under article | ||
183 | 11 of the WIPO copyright treaty adopted on 20 December 1996, or | ||
184 | similar laws prohibiting or restricting circumvention of such | ||
185 | measures. | ||
186 | |||
187 | When you convey a covered work, you waive any legal power to forbid | ||
188 | circumvention of technological measures to the extent such circumvention | ||
189 | is effected by exercising rights under this License with respect to | ||
190 | the covered work, and you disclaim any intention to limit operation or | ||
191 | modification of the work as a means of enforcing, against the work's | ||
192 | users, your or third parties' legal rights to forbid circumvention of | ||
193 | technological measures. | ||
194 | |||
195 | 4. Conveying Verbatim Copies. | ||
196 | |||
197 | You may convey verbatim copies of the Program's source code as you | ||
198 | receive it, in any medium, provided that you conspicuously and | ||
199 | appropriately publish on each copy an appropriate copyright notice; | ||
200 | keep intact all notices stating that this License and any | ||
201 | non-permissive terms added in accord with section 7 apply to the code; | ||
202 | keep intact all notices of the absence of any warranty; and give all | ||
203 | recipients a copy of this License along with the Program. | ||
204 | |||
205 | You may charge any price or no price for each copy that you convey, | ||
206 | and you may offer support or warranty protection for a fee. | ||
207 | |||
208 | 5. Conveying Modified Source Versions. | ||
209 | |||
210 | You may convey a work based on the Program, or the modifications to | ||
211 | produce it from the Program, in the form of source code under the | ||
212 | terms of section 4, provided that you also meet all of these conditions: | ||
213 | |||
214 | a) The work must carry prominent notices stating that you modified | ||
215 | it, and giving a relevant date. | ||
216 | |||
217 | b) The work must carry prominent notices stating that it is | ||
218 | released under this License and any conditions added under section | ||
219 | 7. This requirement modifies the requirement in section 4 to | ||
220 | "keep intact all notices". | ||
221 | |||
222 | c) You must license the entire work, as a whole, under this | ||
223 | License to anyone who comes into possession of a copy. This | ||
224 | License will therefore apply, along with any applicable section 7 | ||
225 | additional terms, to the whole of the work, and all its parts, | ||
226 | regardless of how they are packaged. This License gives no | ||
227 | permission to license the work in any other way, but it does not | ||
228 | invalidate such permission if you have separately received it. | ||
229 | |||
230 | d) If the work has interactive user interfaces, each must display | ||
231 | Appropriate Legal Notices; however, if the Program has interactive | ||
232 | interfaces that do not display Appropriate Legal Notices, your | ||
233 | work need not make them do so. | ||
234 | |||
235 | A compilation of a covered work with other separate and independent | ||
236 | works, which are not by their nature extensions of the covered work, | ||
237 | and which are not combined with it such as to form a larger program, | ||
238 | in or on a volume of a storage or distribution medium, is called an | ||
239 | "aggregate" if the compilation and its resulting copyright are not | ||
240 | used to limit the access or legal rights of the compilation's users | ||
241 | beyond what the individual works permit. Inclusion of a covered work | ||
242 | in an aggregate does not cause this License to apply to the other | ||
243 | parts of the aggregate. | ||
244 | |||
245 | 6. Conveying Non-Source Forms. | ||
246 | |||
247 | You may convey a covered work in object code form under the terms | ||
248 | of sections 4 and 5, provided that you also convey the | ||
249 | machine-readable Corresponding Source under the terms of this License, | ||
250 | in one of these ways: | ||
251 | |||
252 | a) Convey the object code in, or embodied in, a physical product | ||
253 | (including a physical distribution medium), accompanied by the | ||
254 | Corresponding Source fixed on a durable physical medium | ||
255 | customarily used for software interchange. | ||
256 | |||
257 | b) Convey the object code in, or embodied in, a physical product | ||
258 | (including a physical distribution medium), accompanied by a | ||
259 | written offer, valid for at least three years and valid for as | ||
260 | long as you offer spare parts or customer support for that product | ||
261 | model, to give anyone who possesses the object code either (1) a | ||
262 | copy of the Corresponding Source for all the software in the | ||
263 | product that is covered by this License, on a durable physical | ||
264 | medium customarily used for software interchange, for a price no | ||
265 | more than your reasonable cost of physically performing this | ||
266 | conveying of source, or (2) access to copy the | ||
267 | Corresponding Source from a network server at no charge. | ||
268 | |||
269 | c) Convey individual copies of the object code with a copy of the | ||
270 | written offer to provide the Corresponding Source. This | ||
271 | alternative is allowed only occasionally and noncommercially, and | ||
272 | only if you received the object code with such an offer, in accord | ||
273 | with subsection 6b. | ||
274 | |||
275 | d) Convey the object code by offering access from a designated | ||
276 | place (gratis or for a charge), and offer equivalent access to the | ||
277 | Corresponding Source in the same way through the same place at no | ||
278 | further charge. You need not require recipients to copy the | ||
279 | Corresponding Source along with the object code. If the place to | ||
280 | copy the object code is a network server, the Corresponding Source | ||
281 | may be on a different server (operated by you or a third party) | ||
282 | that supports equivalent copying facilities, provided you maintain | ||
283 | clear directions next to the object code saying where to find the | ||
284 | Corresponding Source. Regardless of what server hosts the | ||
285 | Corresponding Source, you remain obligated to ensure that it is | ||
286 | available for as long as needed to satisfy these requirements. | ||
287 | |||
288 | e) Convey the object code using peer-to-peer transmission, provided | ||
289 | you inform other peers where the object code and Corresponding | ||
290 | Source of the work are being offered to the general public at no | ||
291 | charge under subsection 6d. | ||
292 | |||
293 | A separable portion of the object code, whose source code is excluded | ||
294 | from the Corresponding Source as a System Library, need not be | ||
295 | included in conveying the object code work. | ||
296 | |||
297 | A "User Product" is either (1) a "consumer product", which means any | ||
298 | tangible personal property which is normally used for personal, family, | ||
299 | or household purposes, or (2) anything designed or sold for incorporation | ||
300 | into a dwelling. In determining whether a product is a consumer product, | ||
301 | doubtful cases shall be resolved in favor of coverage. For a particular | ||
302 | product received by a particular user, "normally used" refers to a | ||
303 | typical or common use of that class of product, regardless of the status | ||
304 | of the particular user or of the way in which the particular user | ||
305 | actually uses, or expects or is expected to use, the product. A product | ||
306 | is a consumer product regardless of whether the product has substantial | ||
307 | commercial, industrial or non-consumer uses, unless such uses represent | ||
308 | the only significant mode of use of the product. | ||
309 | |||
310 | "Installation Information" for a User Product means any methods, | ||
311 | procedures, authorization keys, or other information required to install | ||
312 | and execute modified versions of a covered work in that User Product from | ||
313 | a modified version of its Corresponding Source. The information must | ||
314 | suffice to ensure that the continued functioning of the modified object | ||
315 | code is in no case prevented or interfered with solely because | ||
316 | modification has been made. | ||
317 | |||
318 | If you convey an object code work under this section in, or with, or | ||
319 | specifically for use in, a User Product, and the conveying occurs as | ||
320 | part of a transaction in which the right of possession and use of the | ||
321 | User Product is transferred to the recipient in perpetuity or for a | ||
322 | fixed term (regardless of how the transaction is characterized), the | ||
323 | Corresponding Source conveyed under this section must be accompanied | ||
324 | by the Installation Information. But this requirement does not apply | ||
325 | if neither you nor any third party retains the ability to install | ||
326 | modified object code on the User Product (for example, the work has | ||
327 | been installed in ROM). | ||
328 | |||
329 | The requirement to provide Installation Information does not include a | ||
330 | requirement to continue to provide support service, warranty, or updates | ||
331 | for a work that has been modified or installed by the recipient, or for | ||
332 | the User Product in which it has been modified or installed. Access to a | ||
333 | network may be denied when the modification itself materially and | ||
334 | adversely affects the operation of the network or violates the rules and | ||
335 | protocols for communication across the network. | ||
336 | |||
337 | Corresponding Source conveyed, and Installation Information provided, | ||
338 | in accord with this section must be in a format that is publicly | ||
339 | documented (and with an implementation available to the public in | ||
340 | source code form), and must require no special password or key for | ||
341 | unpacking, reading or copying. | ||
342 | |||
343 | 7. Additional Terms. | ||
344 | |||
345 | "Additional permissions" are terms that supplement the terms of this | ||
346 | License by making exceptions from one or more of its conditions. | ||
347 | Additional permissions that are applicable to the entire Program shall | ||
348 | be treated as though they were included in this License, to the extent | ||
349 | that they are valid under applicable law. If additional permissions | ||
350 | apply only to part of the Program, that part may be used separately | ||
351 | under those permissions, but the entire Program remains governed by | ||
352 | this License without regard to the additional permissions. | ||
353 | |||
354 | When you convey a copy of a covered work, you may at your option | ||
355 | remove any additional permissions from that copy, or from any part of | ||
356 | it. (Additional permissions may be written to require their own | ||
357 | removal in certain cases when you modify the work.) You may place | ||
358 | additional permissions on material, added by you to a covered work, | ||
359 | for which you have or can give appropriate copyright permission. | ||
360 | |||
361 | Notwithstanding any other provision of this License, for material you | ||
362 | add to a covered work, you may (if authorized by the copyright holders of | ||
363 | that material) supplement the terms of this License with terms: | ||
364 | |||
365 | a) Disclaiming warranty or limiting liability differently from the | ||
366 | terms of sections 15 and 16 of this License; or | ||
367 | |||
368 | b) Requiring preservation of specified reasonable legal notices or | ||
369 | author attributions in that material or in the Appropriate Legal | ||
370 | Notices displayed by works containing it; or | ||
371 | |||
372 | c) Prohibiting misrepresentation of the origin of that material, or | ||
373 | requiring that modified versions of such material be marked in | ||
374 | reasonable ways as different from the original version; or | ||
375 | |||
376 | d) Limiting the use for publicity purposes of names of licensors or | ||
377 | authors of the material; or | ||
378 | |||
379 | e) Declining to grant rights under trademark law for use of some | ||
380 | trade names, trademarks, or service marks; or | ||
381 | |||
382 | f) Requiring indemnification of licensors and authors of that | ||
383 | material by anyone who conveys the material (or modified versions of | ||
384 | it) with contractual assumptions of liability to the recipient, for | ||
385 | any liability that these contractual assumptions directly impose on | ||
386 | those licensors and authors. | ||
387 | |||
388 | All other non-permissive additional terms are considered "further | ||
389 | restrictions" within the meaning of section 10. If the Program as you | ||
390 | received it, or any part of it, contains a notice stating that it is | ||
391 | governed by this License along with a term that is a further | ||
392 | restriction, you may remove that term. If a license document contains | ||
393 | a further restriction but permits relicensing or conveying under this | ||
394 | License, you may add to a covered work material governed by the terms | ||
395 | of that license document, provided that the further restriction does | ||
396 | not survive such relicensing or conveying. | ||
397 | |||
398 | If you add terms to a covered work in accord with this section, you | ||
399 | must place, in the relevant source files, a statement of the | ||
400 | additional terms that apply to those files, or a notice indicating | ||
401 | where to find the applicable terms. | ||
402 | |||
403 | Additional terms, permissive or non-permissive, may be stated in the | ||
404 | form of a separately written license, or stated as exceptions; | ||
405 | the above requirements apply either way. | ||
406 | |||
407 | 8. Termination. | ||
408 | |||
409 | You may not propagate or modify a covered work except as expressly | ||
410 | provided under this License. Any attempt otherwise to propagate or | ||
411 | modify it is void, and will automatically terminate your rights under | ||
412 | this License (including any patent licenses granted under the third | ||
413 | paragraph of section 11). | ||
414 | |||
415 | However, if you cease all violation of this License, then your | ||
416 | license from a particular copyright holder is reinstated (a) | ||
417 | provisionally, unless and until the copyright holder explicitly and | ||
418 | finally terminates your license, and (b) permanently, if the copyright | ||
419 | holder fails to notify you of the violation by some reasonable means | ||
420 | prior to 60 days after the cessation. | ||
421 | |||
422 | Moreover, your license from a particular copyright holder is | ||
423 | reinstated permanently if the copyright holder notifies you of the | ||
424 | violation by some reasonable means, this is the first time you have | ||
425 | received notice of violation of this License (for any work) from that | ||
426 | copyright holder, and you cure the violation prior to 30 days after | ||
427 | your receipt of the notice. | ||
428 | |||
429 | Termination of your rights under this section does not terminate the | ||
430 | licenses of parties who have received copies or rights from you under | ||
431 | this License. If your rights have been terminated and not permanently | ||
432 | reinstated, you do not qualify to receive new licenses for the same | ||
433 | material under section 10. | ||
434 | |||
435 | 9. Acceptance Not Required for Having Copies. | ||
436 | |||
437 | You are not required to accept this License in order to receive or | ||
438 | run a copy of the Program. Ancillary propagation of a covered work | ||
439 | occurring solely as a consequence of using peer-to-peer transmission | ||
440 | to receive a copy likewise does not require acceptance. However, | ||
441 | nothing other than this License grants you permission to propagate or | ||
442 | modify any covered work. These actions infringe copyright if you do | ||
443 | not accept this License. Therefore, by modifying or propagating a | ||
444 | covered work, you indicate your acceptance of this License to do so. | ||
445 | |||
446 | 10. Automatic Licensing of Downstream Recipients. | ||
447 | |||
448 | Each time you convey a covered work, the recipient automatically | ||
449 | receives a license from the original licensors, to run, modify and | ||
450 | propagate that work, subject to this License. You are not responsible | ||
451 | for enforcing compliance by third parties with this License. | ||
452 | |||
453 | An "entity transaction" is a transaction transferring control of an | ||
454 | organization, or substantially all assets of one, or subdividing an | ||
455 | organization, or merging organizations. If propagation of a covered | ||
456 | work results from an entity transaction, each party to that | ||
457 | transaction who receives a copy of the work also receives whatever | ||
458 | licenses to the work the party's predecessor in interest had or could | ||
459 | give under the previous paragraph, plus a right to possession of the | ||
460 | Corresponding Source of the work from the predecessor in interest, if | ||
461 | the predecessor has it or can get it with reasonable efforts. | ||
462 | |||
463 | You may not impose any further restrictions on the exercise of the | ||
464 | rights granted or affirmed under this License. For example, you may | ||
465 | not impose a license fee, royalty, or other charge for exercise of | ||
466 | rights granted under this License, and you may not initiate litigation | ||
467 | (including a cross-claim or counterclaim in a lawsuit) alleging that | ||
468 | any patent claim is infringed by making, using, selling, offering for | ||
469 | sale, or importing the Program or any portion of it. | ||
470 | |||
471 | 11. Patents. | ||
472 | |||
473 | A "contributor" is a copyright holder who authorizes use under this | ||
474 | License of the Program or a work on which the Program is based. The | ||
475 | work thus licensed is called the contributor's "contributor version". | ||
476 | |||
477 | A contributor's "essential patent claims" are all patent claims | ||
478 | owned or controlled by the contributor, whether already acquired or | ||
479 | hereafter acquired, that would be infringed by some manner, permitted | ||
480 | by this License, of making, using, or selling its contributor version, | ||
481 | but do not include claims that would be infringed only as a | ||
482 | consequence of further modification of the contributor version. For | ||
483 | purposes of this definition, "control" includes the right to grant | ||
484 | patent sublicenses in a manner consistent with the requirements of | ||
485 | this License. | ||
486 | |||
487 | Each contributor grants you a non-exclusive, worldwide, royalty-free | ||
488 | patent license under the contributor's essential patent claims, to | ||
489 | make, use, sell, offer for sale, import and otherwise run, modify and | ||
490 | propagate the contents of its contributor version. | ||
491 | |||
492 | In the following three paragraphs, a "patent license" is any express | ||
493 | agreement or commitment, however denominated, not to enforce a patent | ||
494 | (such as an express permission to practice a patent or covenant not to | ||
495 | sue for patent infringement). To "grant" such a patent license to a | ||
496 | party means to make such an agreement or commitment not to enforce a | ||
497 | patent against the party. | ||
498 | |||
499 | If you convey a covered work, knowingly relying on a patent license, | ||
500 | and the Corresponding Source of the work is not available for anyone | ||
501 | to copy, free of charge and under the terms of this License, through a | ||
502 | publicly available network server or other readily accessible means, | ||
503 | then you must either (1) cause the Corresponding Source to be so | ||
504 | available, or (2) arrange to deprive yourself of the benefit of the | ||
505 | patent license for this particular work, or (3) arrange, in a manner | ||
506 | consistent with the requirements of this License, to extend the patent | ||
507 | license to downstream recipients. "Knowingly relying" means you have | ||
508 | actual knowledge that, but for the patent license, your conveying the | ||
509 | covered work in a country, or your recipient's use of the covered work | ||
510 | in a country, would infringe one or more identifiable patents in that | ||
511 | country that you have reason to believe are valid. | ||
512 | |||
513 | If, pursuant to or in connection with a single transaction or | ||
514 | arrangement, you convey, or propagate by procuring conveyance of, a | ||
515 | covered work, and grant a patent license to some of the parties | ||
516 | receiving the covered work authorizing them to use, propagate, modify | ||
517 | or convey a specific copy of the covered work, then the patent license | ||
518 | you grant is automatically extended to all recipients of the covered | ||
519 | work and works based on it. | ||
520 | |||
521 | A patent license is "discriminatory" if it does not include within | ||
522 | the scope of its coverage, prohibits the exercise of, or is | ||
523 | conditioned on the non-exercise of one or more of the rights that are | ||
524 | specifically granted under this License. You may not convey a covered | ||
525 | work if you are a party to an arrangement with a third party that is | ||
526 | in the business of distributing software, under which you make payment | ||
527 | to the third party based on the extent of your activity of conveying | ||
528 | the work, and under which the third party grants, to any of the | ||
529 | parties who would receive the covered work from you, a discriminatory | ||
530 | patent license (a) in connection with copies of the covered work | ||
531 | conveyed by you (or copies made from those copies), or (b) primarily | ||
532 | for and in connection with specific products or compilations that | ||
533 | contain the covered work, unless you entered into that arrangement, | ||
534 | or that patent license was granted, prior to 28 March 2007. | ||
535 | |||
536 | Nothing in this License shall be construed as excluding or limiting | ||
537 | any implied license or other defenses to infringement that may | ||
538 | otherwise be available to you under applicable patent law. | ||
539 | |||
540 | 12. No Surrender of Others' Freedom. | ||
541 | |||
542 | If conditions are imposed on you (whether by court order, agreement or | ||
543 | otherwise) that contradict the conditions of this License, they do not | ||
544 | excuse you from the conditions of this License. If you cannot convey a | ||
545 | covered work so as to satisfy simultaneously your obligations under this | ||
546 | License and any other pertinent obligations, then as a consequence you may | ||
547 | not convey it at all. For example, if you agree to terms that obligate you | ||
548 | to collect a royalty for further conveying from those to whom you convey | ||
549 | the Program, the only way you could satisfy both those terms and this | ||
550 | License would be to refrain entirely from conveying the Program. | ||
551 | |||
552 | 13. Use with the GNU Affero General Public License. | ||
553 | |||
554 | Notwithstanding any other provision of this License, you have | ||
555 | permission to link or combine any covered work with a work licensed | ||
556 | under version 3 of the GNU Affero General Public License into a single | ||
557 | combined work, and to convey the resulting work. The terms of this | ||
558 | License will continue to apply to the part which is the covered work, | ||
559 | but the special requirements of the GNU Affero General Public License, | ||
560 | section 13, concerning interaction through a network will apply to the | ||
561 | combination as such. | ||
562 | |||
563 | 14. Revised Versions of this License. | ||
564 | |||
565 | The Free Software Foundation may publish revised and/or new versions of | ||
566 | the GNU General Public License from time to time. Such new versions will | ||
567 | be similar in spirit to the present version, but may differ in detail to | ||
568 | address new problems or concerns. | ||
569 | |||
570 | Each version is given a distinguishing version number. If the | ||
571 | Program specifies that a certain numbered version of the GNU General | ||
572 | Public License "or any later version" applies to it, you have the | ||
573 | option of following the terms and conditions either of that numbered | ||
574 | version or of any later version published by the Free Software | ||
575 | Foundation. If the Program does not specify a version number of the | ||
576 | GNU General Public License, you may choose any version ever published | ||
577 | by the Free Software Foundation. | ||
578 | |||
579 | If the Program specifies that a proxy can decide which future | ||
580 | versions of the GNU General Public License can be used, that proxy's | ||
581 | public statement of acceptance of a version permanently authorizes you | ||
582 | to choose that version for the Program. | ||
583 | |||
584 | Later license versions may give you additional or different | ||
585 | permissions. However, no additional obligations are imposed on any | ||
586 | author or copyright holder as a result of your choosing to follow a | ||
587 | later version. | ||
588 | |||
589 | 15. Disclaimer of Warranty. | ||
590 | |||
591 | THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY | ||
592 | APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT | ||
593 | HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY | ||
594 | OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, | ||
595 | THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||
596 | PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM | ||
597 | IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF | ||
598 | ALL NECESSARY SERVICING, REPAIR OR CORRECTION. | ||
599 | |||
600 | 16. Limitation of Liability. | ||
601 | |||
602 | IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING | ||
603 | WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS | ||
604 | THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY | ||
605 | GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE | ||
606 | USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF | ||
607 | DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD | ||
608 | PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), | ||
609 | EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF | ||
610 | SUCH DAMAGES. | ||
611 | |||
612 | 17. Interpretation of Sections 15 and 16. | ||
613 | |||
614 | If the disclaimer of warranty and limitation of liability provided | ||
615 | above cannot be given local legal effect according to their terms, | ||
616 | reviewing courts shall apply local law that most closely approximates | ||
617 | an absolute waiver of all civil liability in connection with the | ||
618 | Program, unless a warranty or assumption of liability accompanies a | ||
619 | copy of the Program in return for a fee. | ||
620 | |||
621 | END OF TERMS AND CONDITIONS | ||
622 | |||
623 | How to Apply These Terms to Your New Programs | ||
624 | |||
625 | If you develop a new program, and you want it to be of the greatest | ||
626 | possible use to the public, the best way to achieve this is to make it | ||
627 | free software which everyone can redistribute and change under these terms. | ||
628 | |||
629 | To do so, attach the following notices to the program. It is safest | ||
630 | to attach them to the start of each source file to most effectively | ||
631 | state the exclusion of warranty; and each file should have at least | ||
632 | the "copyright" line and a pointer to where the full notice is found. | ||
633 | |||
634 | <one line to give the program's name and a brief idea of what it does.> | ||
635 | Copyright (C) <year> <name of author> | ||
636 | |||
637 | This program is free software: you can redistribute it and/or modify | ||
638 | it under the terms of the GNU General Public License as published by | ||
639 | the Free Software Foundation, either version 3 of the License, or | ||
640 | (at your option) any later version. | ||
641 | |||
642 | This program is distributed in the hope that it will be useful, | ||
643 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
644 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
645 | GNU General Public License for more details. | ||
646 | |||
647 | You should have received a copy of the GNU General Public License | ||
648 | along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
649 | |||
650 | Also add information on how to contact you by electronic and paper mail. | ||
651 | |||
652 | If the program does terminal interaction, make it output a short | ||
653 | notice like this when it starts in an interactive mode: | ||
654 | |||
655 | <program> Copyright (C) <year> <name of author> | ||
656 | This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. | ||
657 | This is free software, and you are welcome to redistribute it | ||
658 | under certain conditions; type `show c' for details. | ||
659 | |||
660 | The hypothetical commands `show w' and `show c' should show the appropriate | ||
661 | parts of the General Public License. Of course, your program's commands | ||
662 | might be different; for a GUI interface, you would use an "about box". | ||
663 | |||
664 | You should also get your employer (if you work as a programmer) or school, | ||
665 | if any, to sign a "copyright disclaimer" for the program, if necessary. | ||
666 | For more information on this, and how to apply and follow the GNU GPL, see | ||
667 | <http://www.gnu.org/licenses/>. | ||
668 | |||
669 | The GNU General Public License does not permit incorporating your program | ||
670 | into proprietary programs. If your program is a subroutine library, you | ||
671 | may consider it more useful to permit linking proprietary applications with | ||
672 | the library. If this is what you want to do, use the GNU Lesser General | ||
673 | Public License instead of this License. But first, please read | ||
674 | <http://www.gnu.org/philosophy/why-not-lgpl.html>. | ||
@@ -0,0 +1,46 @@ | |||
1 | INTRODUCTION: | ||
2 | |||
3 | ExiFilm is a suite of programs that can be used to annotate digital | ||
4 | images with information about the film exposure used to create them. | ||
5 | In particular, it is designed for use with large format film cameras | ||
6 | where the photographer may then scan the film to create a digital copy | ||
7 | for a library or for digital processing. | ||
8 | |||
9 | By storing the exposure metadata in EXIF tags of scanned images, the | ||
10 | photographer can have electronic access to the same information | ||
11 | contained in the written record from the field from within an image | ||
12 | viewer. Further processing of the data can be done without the need | ||
13 | to store the metadata in a separate database. | ||
14 | |||
15 | THE PROGRAMS: | ||
16 | |||
17 | The file "lfrecord.ps" is a PostScript file that can be printed on US | ||
18 | letter paper (or other sizes). It is a single page of four exposure | ||
19 | record forms design for large format photography. The author trims | ||
20 | the four forms and binds them together as a notepad to take into the | ||
21 | field. The PostScript program is hand-written and can be altered | ||
22 | fairly easily. | ||
23 | |||
24 | The Python program "exifilm.py" provides a data entry screen similar | ||
25 | to the form in "lfrecord.ps". It takes an optional argument of a path | ||
26 | to a directory with JPEG image files. It will provide a drop-down | ||
27 | list of JPEG files in the directory, and selecting one of the files | ||
28 | will load the EXIF information from that file. In this way it allows | ||
29 | the user to quickly enter metadata for a number of scanned film | ||
30 | images. The metadata are saved immediately upon loading a new file or | ||
31 | exiting the program. | ||
32 | |||
33 | The Python program "printrecord.py" loads the metadata previously | ||
34 | entered with "exifilm.py" and produces pages similar to those in | ||
35 | "lfrecord.ps" with the metadata typeset into the fields. The | ||
36 | resulting file may then be printed and bound into a photo archive with | ||
37 | the original film. Example usage: | ||
38 | |||
39 | python printrecord.py /path/to/images 1 16 | lpr | ||
40 | |||
41 | Produces four pages of output including the metadata for image IDs 1 | ||
42 | through 16. | ||
43 | |||
44 | |||
45 | James E. Blair <corvus@gnu.org> | ||
46 | October, 2009 | ||
diff --git a/exifilm.glade b/exifilm.glade new file mode 100644 index 0000000..7ae4660 --- /dev/null +++ b/exifilm.glade | |||
@@ -0,0 +1,552 @@ | |||
1 | <?xml version="1.0"?> | ||
2 | <glade-interface> | ||
3 | <!-- interface-requires gtk+ 2.16 --> | ||
4 | <!-- interface-naming-policy toplevel-contextual --> | ||
5 | <widget class="GtkWindow" id="main_window"> | ||
6 | <property name="visible">True</property> | ||
7 | <property name="title" translatable="yes">ExiFilm</property> | ||
8 | <property name="default_width">400</property> | ||
9 | <property name="default_height">500</property> | ||
10 | <signal name="destroy" handler="on_main_window_destroy"/> | ||
11 | <signal name="key_press_event" handler="on_main_window_key_press_event"/> | ||
12 | <child> | ||
13 | <widget class="GtkVBox" id="vbox1"> | ||
14 | <property name="visible">True</property> | ||
15 | <child> | ||
16 | <widget class="GtkHBox" id="hbox1"> | ||
17 | <property name="visible">True</property> | ||
18 | <property name="border_width">5</property> | ||
19 | <property name="spacing">5</property> | ||
20 | <child> | ||
21 | <widget class="GtkLabel" id="label10"> | ||
22 | <property name="visible">True</property> | ||
23 | <property name="label" translatable="yes">File:</property> | ||
24 | </widget> | ||
25 | <packing> | ||
26 | <property name="expand">False</property> | ||
27 | <property name="fill">False</property> | ||
28 | <property name="position">0</property> | ||
29 | </packing> | ||
30 | </child> | ||
31 | <child> | ||
32 | <widget class="GtkComboBox" id="file"> | ||
33 | <property name="visible">True</property> | ||
34 | <signal name="changed" handler="on_file_changed"/> | ||
35 | </widget> | ||
36 | <packing> | ||
37 | <property name="position">1</property> | ||
38 | </packing> | ||
39 | </child> | ||
40 | </widget> | ||
41 | <packing> | ||
42 | <property name="expand">False</property> | ||
43 | <property name="fill">False</property> | ||
44 | <property name="position">0</property> | ||
45 | </packing> | ||
46 | </child> | ||
47 | <child> | ||
48 | <widget class="GtkHSeparator" id="hseparator1"> | ||
49 | <property name="visible">True</property> | ||
50 | </widget> | ||
51 | <packing> | ||
52 | <property name="expand">False</property> | ||
53 | <property name="fill">False</property> | ||
54 | <property name="position">1</property> | ||
55 | </packing> | ||
56 | </child> | ||
57 | <child> | ||
58 | <widget class="GtkTable" id="table1"> | ||
59 | <property name="visible">True</property> | ||
60 | <property name="border_width">5</property> | ||
61 | <property name="n_rows">4</property> | ||
62 | <property name="n_columns">6</property> | ||
63 | <property name="column_spacing">5</property> | ||
64 | <property name="row_spacing">5</property> | ||
65 | <child> | ||
66 | <widget class="GtkEntry" id="film"> | ||
67 | <property name="visible">True</property> | ||
68 | <property name="can_focus">True</property> | ||
69 | <property name="invisible_char">●</property> | ||
70 | <property name="width_chars">6</property> | ||
71 | </widget> | ||
72 | <packing> | ||
73 | <property name="left_attach">1</property> | ||
74 | <property name="right_attach">2</property> | ||
75 | <property name="top_attach">1</property> | ||
76 | <property name="bottom_attach">2</property> | ||
77 | <property name="y_options"></property> | ||
78 | </packing> | ||
79 | </child> | ||
80 | <child> | ||
81 | <widget class="GtkEntry" id="aperture"> | ||
82 | <property name="visible">True</property> | ||
83 | <property name="can_focus">True</property> | ||
84 | <property name="invisible_char">●</property> | ||
85 | <property name="width_chars">6</property> | ||
86 | </widget> | ||
87 | <packing> | ||
88 | <property name="left_attach">1</property> | ||
89 | <property name="right_attach">3</property> | ||
90 | <property name="top_attach">3</property> | ||
91 | <property name="bottom_attach">4</property> | ||
92 | <property name="y_options"></property> | ||
93 | </packing> | ||
94 | </child> | ||
95 | <child> | ||
96 | <widget class="GtkEntry" id="shutter"> | ||
97 | <property name="visible">True</property> | ||
98 | <property name="can_focus">True</property> | ||
99 | <property name="invisible_char">●</property> | ||
100 | <property name="width_chars">6</property> | ||
101 | </widget> | ||
102 | <packing> | ||
103 | <property name="left_attach">3</property> | ||
104 | <property name="right_attach">5</property> | ||
105 | <property name="top_attach">3</property> | ||
106 | <property name="bottom_attach">4</property> | ||
107 | <property name="y_options"></property> | ||
108 | </packing> | ||
109 | </child> | ||
110 | <child> | ||
111 | <widget class="GtkEntry" id="carrier"> | ||
112 | <property name="visible">True</property> | ||
113 | <property name="can_focus">True</property> | ||
114 | <property name="invisible_char">●</property> | ||
115 | <property name="width_chars">4</property> | ||
116 | </widget> | ||
117 | <packing> | ||
118 | <property name="left_attach">2</property> | ||
119 | <property name="right_attach">4</property> | ||
120 | <property name="top_attach">1</property> | ||
121 | <property name="bottom_attach">2</property> | ||
122 | <property name="y_options"></property> | ||
123 | </packing> | ||
124 | </child> | ||
125 | <child> | ||
126 | <widget class="GtkEntry" id="process"> | ||
127 | <property name="visible">True</property> | ||
128 | <property name="can_focus">True</property> | ||
129 | <property name="invisible_char">●</property> | ||
130 | <property name="width_chars">4</property> | ||
131 | </widget> | ||
132 | <packing> | ||
133 | <property name="left_attach">4</property> | ||
134 | <property name="right_attach">5</property> | ||
135 | <property name="top_attach">1</property> | ||
136 | <property name="bottom_attach">2</property> | ||
137 | <property name="y_options"></property> | ||
138 | </packing> | ||
139 | </child> | ||
140 | <child> | ||
141 | <widget class="GtkLabel" id="label1"> | ||
142 | <property name="visible">True</property> | ||
143 | <property name="label" translatable="yes">ID</property> | ||
144 | </widget> | ||
145 | <packing> | ||
146 | <property name="x_options">GTK_FILL</property> | ||
147 | <property name="y_options"></property> | ||
148 | </packing> | ||
149 | </child> | ||
150 | <child> | ||
151 | <widget class="GtkLabel" id="label2"> | ||
152 | <property name="visible">True</property> | ||
153 | <property name="label" translatable="yes">Film</property> | ||
154 | </widget> | ||
155 | <packing> | ||
156 | <property name="left_attach">1</property> | ||
157 | <property name="right_attach">2</property> | ||
158 | <property name="x_options">GTK_FILL</property> | ||
159 | <property name="y_options"></property> | ||
160 | </packing> | ||
161 | </child> | ||
162 | <child> | ||
163 | <widget class="GtkLabel" id="label3"> | ||
164 | <property name="visible">True</property> | ||
165 | <property name="label" translatable="yes">Carrier</property> | ||
166 | </widget> | ||
167 | <packing> | ||
168 | <property name="left_attach">2</property> | ||
169 | <property name="right_attach">4</property> | ||
170 | <property name="x_options">GTK_FILL</property> | ||
171 | <property name="y_options"></property> | ||
172 | </packing> | ||
173 | </child> | ||
174 | <child> | ||
175 | <widget class="GtkLabel" id="label4"> | ||
176 | <property name="visible">True</property> | ||
177 | <property name="label" translatable="yes">Process</property> | ||
178 | </widget> | ||
179 | <packing> | ||
180 | <property name="left_attach">4</property> | ||
181 | <property name="right_attach">5</property> | ||
182 | <property name="x_options">GTK_FILL</property> | ||
183 | <property name="y_options"></property> | ||
184 | </packing> | ||
185 | </child> | ||
186 | <child> | ||
187 | <widget class="GtkLabel" id="label5"> | ||
188 | <property name="visible">True</property> | ||
189 | <property name="label" translatable="yes">Front Movement</property> | ||
190 | </widget> | ||
191 | <packing> | ||
192 | <property name="left_attach">5</property> | ||
193 | <property name="right_attach">6</property> | ||
194 | <property name="x_options">GTK_FILL</property> | ||
195 | <property name="y_options"></property> | ||
196 | </packing> | ||
197 | </child> | ||
198 | <child> | ||
199 | <widget class="GtkLabel" id="label6"> | ||
200 | <property name="visible">True</property> | ||
201 | <property name="label" translatable="yes">Rear Movement</property> | ||
202 | </widget> | ||
203 | <packing> | ||
204 | <property name="left_attach">5</property> | ||
205 | <property name="right_attach">6</property> | ||
206 | <property name="top_attach">2</property> | ||
207 | <property name="bottom_attach">3</property> | ||
208 | <property name="x_options">GTK_FILL</property> | ||
209 | <property name="y_options"></property> | ||
210 | </packing> | ||
211 | </child> | ||
212 | <child> | ||
213 | <widget class="GtkLabel" id="label7"> | ||
214 | <property name="visible">True</property> | ||
215 | <property name="label" translatable="yes">Lens</property> | ||
216 | </widget> | ||
217 | <packing> | ||
218 | <property name="top_attach">2</property> | ||
219 | <property name="bottom_attach">3</property> | ||
220 | <property name="x_options">GTK_FILL</property> | ||
221 | <property name="y_options"></property> | ||
222 | </packing> | ||
223 | </child> | ||
224 | <child> | ||
225 | <widget class="GtkLabel" id="label8"> | ||
226 | <property name="visible">True</property> | ||
227 | <property name="label" translatable="yes">Aperture</property> | ||
228 | </widget> | ||
229 | <packing> | ||
230 | <property name="left_attach">1</property> | ||
231 | <property name="right_attach">3</property> | ||
232 | <property name="top_attach">2</property> | ||
233 | <property name="bottom_attach">3</property> | ||
234 | <property name="x_options">GTK_FILL</property> | ||
235 | <property name="y_options"></property> | ||
236 | </packing> | ||
237 | </child> | ||
238 | <child> | ||
239 | <widget class="GtkLabel" id="label9"> | ||
240 | <property name="visible">True</property> | ||
241 | <property name="label" translatable="yes">Shutter</property> | ||
242 | </widget> | ||
243 | <packing> | ||
244 | <property name="left_attach">3</property> | ||
245 | <property name="right_attach">5</property> | ||
246 | <property name="top_attach">2</property> | ||
247 | <property name="bottom_attach">3</property> | ||
248 | <property name="x_options">GTK_FILL</property> | ||
249 | <property name="y_options"></property> | ||
250 | </packing> | ||
251 | </child> | ||
252 | <child> | ||
253 | <widget class="GtkEntry" id="id"> | ||
254 | <property name="visible">True</property> | ||
255 | <property name="can_focus">True</property> | ||
256 | <property name="invisible_char">●</property> | ||
257 | <property name="width_chars">4</property> | ||
258 | </widget> | ||
259 | <packing> | ||
260 | <property name="top_attach">1</property> | ||
261 | <property name="bottom_attach">2</property> | ||
262 | <property name="y_options"></property> | ||
263 | </packing> | ||
264 | </child> | ||
265 | <child> | ||
266 | <widget class="GtkEntry" id="lens"> | ||
267 | <property name="visible">True</property> | ||
268 | <property name="can_focus">True</property> | ||
269 | <property name="invisible_char">●</property> | ||
270 | <property name="width_chars">4</property> | ||
271 | </widget> | ||
272 | <packing> | ||
273 | <property name="top_attach">3</property> | ||
274 | <property name="bottom_attach">4</property> | ||
275 | <property name="y_options"></property> | ||
276 | </packing> | ||
277 | </child> | ||
278 | <child> | ||
279 | <widget class="GtkButton" id="front"> | ||
280 | <property name="label" translatable="yes">None</property> | ||
281 | <property name="visible">True</property> | ||
282 | <property name="can_focus">True</property> | ||
283 | <property name="receives_default">True</property> | ||
284 | <signal name="clicked" handler="on_front_clicked"/> | ||
285 | </widget> | ||
286 | <packing> | ||
287 | <property name="left_attach">5</property> | ||
288 | <property name="right_attach">6</property> | ||
289 | <property name="top_attach">1</property> | ||
290 | <property name="bottom_attach">2</property> | ||
291 | </packing> | ||
292 | </child> | ||
293 | <child> | ||
294 | <widget class="GtkButton" id="rear"> | ||
295 | <property name="label" translatable="yes">None</property> | ||
296 | <property name="visible">True</property> | ||
297 | <property name="can_focus">True</property> | ||
298 | <property name="receives_default">True</property> | ||
299 | <signal name="clicked" handler="on_rear_clicked"/> | ||
300 | </widget> | ||
301 | <packing> | ||
302 | <property name="left_attach">5</property> | ||
303 | <property name="right_attach">6</property> | ||
304 | <property name="top_attach">3</property> | ||
305 | <property name="bottom_attach">4</property> | ||
306 | </packing> | ||
307 | </child> | ||
308 | </widget> | ||
309 | <packing> | ||
310 | <property name="expand">False</property> | ||
311 | <property name="fill">False</property> | ||
312 | <property name="position">2</property> | ||
313 | </packing> | ||
314 | </child> | ||
315 | <child> | ||
316 | <widget class="GtkHSeparator" id="hseparator2"> | ||
317 | <property name="visible">True</property> | ||
318 | </widget> | ||
319 | <packing> | ||
320 | <property name="expand">False</property> | ||
321 | <property name="position">3</property> | ||
322 | </packing> | ||
323 | </child> | ||
324 | <child> | ||
325 | <widget class="GtkTable" id="table2"> | ||
326 | <property name="visible">True</property> | ||
327 | <property name="border_width">5</property> | ||
328 | <property name="n_rows">2</property> | ||
329 | <property name="n_columns">2</property> | ||
330 | <property name="column_spacing">5</property> | ||
331 | <property name="row_spacing">5</property> | ||
332 | <child> | ||
333 | <widget class="GtkLabel" id="label11"> | ||
334 | <property name="visible">True</property> | ||
335 | <property name="xalign">0</property> | ||
336 | <property name="label" translatable="yes">Description:</property> | ||
337 | </widget> | ||
338 | <packing> | ||
339 | <property name="x_options">GTK_FILL</property> | ||
340 | </packing> | ||
341 | </child> | ||
342 | <child> | ||
343 | <widget class="GtkLabel" id="label12"> | ||
344 | <property name="visible">True</property> | ||
345 | <property name="xalign">0</property> | ||
346 | <property name="label" translatable="yes">Date:</property> | ||
347 | </widget> | ||
348 | <packing> | ||
349 | <property name="top_attach">1</property> | ||
350 | <property name="bottom_attach">2</property> | ||
351 | <property name="x_options">GTK_FILL</property> | ||
352 | </packing> | ||
353 | </child> | ||
354 | <child> | ||
355 | <widget class="GtkEntry" id="description"> | ||
356 | <property name="visible">True</property> | ||
357 | <property name="can_focus">True</property> | ||
358 | <property name="invisible_char">●</property> | ||
359 | </widget> | ||
360 | <packing> | ||
361 | <property name="left_attach">1</property> | ||
362 | <property name="right_attach">2</property> | ||
363 | </packing> | ||
364 | </child> | ||
365 | <child> | ||
366 | <widget class="GtkHButtonBox" id="hbuttonbox1"> | ||
367 | <property name="visible">True</property> | ||
368 | <property name="layout_style">start</property> | ||
369 | <child> | ||
370 | <widget class="GtkButton" id="date"> | ||
371 | <property name="visible">True</property> | ||
372 | <property name="can_focus">True</property> | ||
373 | <property name="receives_default">True</property> | ||
374 | <signal name="clicked" handler="on_date_clicked"/> | ||
375 | </widget> | ||
376 | <packing> | ||
377 | <property name="expand">False</property> | ||
378 | <property name="fill">False</property> | ||
379 | <property name="position">0</property> | ||
380 | </packing> | ||
381 | </child> | ||
382 | </widget> | ||
383 | <packing> | ||
384 | <property name="left_attach">1</property> | ||
385 | <property name="right_attach">2</property> | ||
386 | <property name="top_attach">1</property> | ||
387 | <property name="bottom_attach">2</property> | ||
388 | </packing> | ||
389 | </child> | ||
390 | </widget> | ||
391 | <packing> | ||
392 | <property name="expand">False</property> | ||
393 | <property name="fill">False</property> | ||
394 | <property name="position">4</property> | ||
395 | </packing> | ||
396 | </child> | ||
397 | <child> | ||
398 | <widget class="GtkHSeparator" id="hseparator3"> | ||
399 | <property name="visible">True</property> | ||
400 | </widget> | ||
401 | <packing> | ||
402 | <property name="expand">False</property> | ||
403 | <property name="position">5</property> | ||
404 | </packing> | ||
405 | </child> | ||
406 | <child> | ||
407 | <widget class="GtkScrolledWindow" id="scrolledwindow1"> | ||
408 | <property name="visible">True</property> | ||
409 | <property name="can_focus">True</property> | ||
410 | <property name="border_width">5</property> | ||
411 | <property name="hscrollbar_policy">automatic</property> | ||
412 | <property name="vscrollbar_policy">automatic</property> | ||
413 | <child> | ||
414 | <widget class="GtkTextView" id="comments"> | ||
415 | <property name="visible">True</property> | ||
416 | <property name="can_focus">True</property> | ||
417 | </widget> | ||
418 | </child> | ||
419 | </widget> | ||
420 | <packing> | ||
421 | <property name="position">6</property> | ||
422 | </packing> | ||
423 | </child> | ||
424 | </widget> | ||
425 | </child> | ||
426 | </widget> | ||
427 | <widget class="GtkDialog" id="calendar_dialog"> | ||
428 | <property name="border_width">5</property> | ||
429 | <property name="type_hint">normal</property> | ||
430 | <property name="has_separator">False</property> | ||
431 | <child internal-child="vbox"> | ||
432 | <widget class="GtkVBox" id="dialog-vbox1"> | ||
433 | <property name="visible">True</property> | ||
434 | <property name="orientation">vertical</property> | ||
435 | <property name="spacing">2</property> | ||
436 | <child> | ||
437 | <widget class="GtkCalendar" id="calendar"> | ||
438 | <property name="visible">True</property> | ||
439 | <property name="can_focus">True</property> | ||
440 | <property name="year">2009</property> | ||
441 | <property name="month">4</property> | ||
442 | <property name="day">27</property> | ||
443 | </widget> | ||
444 | <packing> | ||
445 | <property name="position">1</property> | ||
446 | </packing> | ||
447 | </child> | ||
448 | <child internal-child="action_area"> | ||
449 | <widget class="GtkHButtonBox" id="dialog-action_area1"> | ||
450 | <property name="visible">True</property> | ||
451 | <property name="layout_style">end</property> | ||
452 | <child> | ||
453 | <widget class="GtkButton" id="cancel"> | ||
454 | <property name="label" translatable="yes">gtk-cancel</property> | ||
455 | <property name="visible">True</property> | ||
456 | <property name="can_focus">True</property> | ||
457 | <property name="receives_default">True</property> | ||
458 | <property name="use_stock">True</property> | ||
459 | </widget> | ||
460 | <packing> | ||
461 | <property name="expand">False</property> | ||
462 | <property name="fill">False</property> | ||
463 | <property name="position">0</property> | ||
464 | </packing> | ||
465 | </child> | ||
466 | <child> | ||
467 | <widget class="GtkButton" id="ok"> | ||
468 | <property name="label" translatable="yes">gtk-ok</property> | ||
469 | <property name="response_id">1</property> | ||
470 | <property name="visible">True</property> | ||
471 | <property name="can_focus">True</property> | ||
472 | <property name="receives_default">True</property> | ||
473 | <property name="use_stock">True</property> | ||
474 | </widget> | ||
475 | <packing> | ||
476 | <property name="expand">False</property> | ||
477 | <property name="fill">False</property> | ||
478 | <property name="position">1</property> | ||
479 | </packing> | ||
480 | </child> | ||
481 | </widget> | ||
482 | <packing> | ||
483 | <property name="expand">False</property> | ||
484 | <property name="pack_type">end</property> | ||
485 | <property name="position">0</property> | ||
486 | </packing> | ||
487 | </child> | ||
488 | </widget> | ||
489 | </child> | ||
490 | </widget> | ||
491 | <widget class="GtkDialog" id="movement_dialog"> | ||
492 | <property name="border_width">5</property> | ||
493 | <property name="type_hint">normal</property> | ||
494 | <property name="has_separator">False</property> | ||
495 | <child internal-child="vbox"> | ||
496 | <widget class="GtkVBox" id="dialog-vbox2"> | ||
497 | <property name="visible">True</property> | ||
498 | <property name="orientation">vertical</property> | ||
499 | <property name="spacing">2</property> | ||
500 | <child> | ||
501 | <widget class="GtkTreeView" id="movements"> | ||
502 | <property name="visible">True</property> | ||
503 | <property name="can_focus">True</property> | ||
504 | </widget> | ||
505 | <packing> | ||
506 | <property name="position">1</property> | ||
507 | </packing> | ||
508 | </child> | ||
509 | <child internal-child="action_area"> | ||
510 | <widget class="GtkHButtonBox" id="dialog-action_area2"> | ||
511 | <property name="visible">True</property> | ||
512 | <property name="layout_style">end</property> | ||
513 | <child> | ||
514 | <widget class="GtkButton" id="cancel"> | ||
515 | <property name="label" translatable="yes">gtk-cancel</property> | ||
516 | <property name="visible">True</property> | ||
517 | <property name="can_focus">True</property> | ||
518 | <property name="receives_default">True</property> | ||
519 | <property name="use_stock">True</property> | ||
520 | </widget> | ||
521 | <packing> | ||
522 | <property name="expand">False</property> | ||
523 | <property name="fill">False</property> | ||
524 | <property name="position">0</property> | ||
525 | </packing> | ||
526 | </child> | ||
527 | <child> | ||
528 | <widget class="GtkButton" id="ok"> | ||
529 | <property name="label" translatable="yes">gtk-ok</property> | ||
530 | <property name="response_id">1</property> | ||
531 | <property name="visible">True</property> | ||
532 | <property name="can_focus">True</property> | ||
533 | <property name="receives_default">True</property> | ||
534 | <property name="use_stock">True</property> | ||
535 | </widget> | ||
536 | <packing> | ||
537 | <property name="expand">False</property> | ||
538 | <property name="fill">False</property> | ||
539 | <property name="position">1</property> | ||
540 | </packing> | ||
541 | </child> | ||
542 | </widget> | ||
543 | <packing> | ||
544 | <property name="expand">False</property> | ||
545 | <property name="pack_type">end</property> | ||
546 | <property name="position">0</property> | ||
547 | </packing> | ||
548 | </child> | ||
549 | </widget> | ||
550 | </child> | ||
551 | </widget> | ||
552 | </glade-interface> | ||
diff --git a/exifilm.gladep b/exifilm.gladep new file mode 100644 index 0000000..407c797 --- /dev/null +++ b/exifilm.gladep | |||
@@ -0,0 +1,8 @@ | |||
1 | <?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> | ||
2 | <!DOCTYPE glade-project SYSTEM "http://glade.gnome.org/glade-project-2.0.dtd"> | ||
3 | |||
4 | <glade-project> | ||
5 | <name>Exifilm</name> | ||
6 | <program_name>exifilm</program_name> | ||
7 | <gnome_support>FALSE</gnome_support> | ||
8 | </glade-project> | ||
diff --git a/exifilm.py b/exifilm.py new file mode 100644 index 0000000..17db62d --- /dev/null +++ b/exifilm.py | |||
@@ -0,0 +1,383 @@ | |||
1 | #!/usr/bin/python | ||
2 | |||
3 | # ExiFilm -- Add film exposure metadata to EXIF tags of digital images | ||
4 | # Copyright (C) 2009 James E. Blair <corvus@gnu.org> | ||
5 | # | ||
6 | # This program is free software: you can redistribute it and/or modify | ||
7 | # it under the terms of the GNU General Public License as published by | ||
8 | # the Free Software Foundation, either version 3 of the License, or | ||
9 | # (at your option) any later version. | ||
10 | # | ||
11 | # This program is distributed in the hope that it will be useful, | ||
12 | # but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | # GNU General Public License for more details. | ||
15 | # | ||
16 | # You should have received a copy of the GNU General Public License | ||
17 | # along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
18 | |||
19 | import pygtk | ||
20 | pygtk.require('2.0') | ||
21 | import gtk, gobject | ||
22 | import gtk.glade | ||
23 | import gtk.keysyms | ||
24 | from gtk import gdk | ||
25 | |||
26 | import os, sys | ||
27 | import pyexiv2 | ||
28 | import datetime | ||
29 | import decimal, fractions | ||
30 | import re | ||
31 | |||
32 | HALF_STOP_SCALE = ['1', '1.2', '1.4', '1.7', '2', '2.4', '2.8', '3.3', '4', '4.8', | ||
33 | '5.6', '6.7', '8', '9.5', '11', '13', '16', '19', '22', '27', | ||
34 | '32', '38', '45', '54', '64', '76', '91'] | ||
35 | |||
36 | |||
37 | THIRD_STOP_SCALE = ['1', '1.1', '1.2', '1.4', '1.6', '1.8', '2', '2.2', '2.5', | ||
38 | '2.8', '3.2', '3.5', '4', '4.5', '5.0', '5.6', '6.3', '7.1', | ||
39 | '8', '9', '10', '11', '13', '14', '16', '18', '20', '22', | ||
40 | '25', '29', '32', '36', '40', '45', '51', '57', '64', '72', | ||
41 | '81', '91'] | ||
42 | |||
43 | CAMERA_MOVEMENTS = [ | ||
44 | 'rising', | ||
45 | 'falling', | ||
46 | 'forward tilt', | ||
47 | 'backward tilt', | ||
48 | 'left shift', | ||
49 | 'right shift', | ||
50 | 'left swing', | ||
51 | 'right swing', | ||
52 | ] | ||
53 | |||
54 | ID = 'ID' | ||
55 | FILM = 'Film' | ||
56 | CARRIER = 'Carrier' | ||
57 | PROCESS = 'Process' | ||
58 | FRONT_MOVEMENTS = 'Front movements' | ||
59 | REAR_MOVEMENTS = 'Rear movements' | ||
60 | |||
61 | PRIVATE_KEYS = [ | ||
62 | ID, | ||
63 | FILM, | ||
64 | CARRIER, | ||
65 | PROCESS, | ||
66 | FRONT_MOVEMENTS, | ||
67 | REAR_MOVEMENTS, | ||
68 | ] | ||
69 | |||
70 | ISO_RE = re.compile(r'\d\d+') | ||
71 | |||
72 | def to_rational(v): | ||
73 | if '/' in v: | ||
74 | n,d = v.split('/') | ||
75 | else: | ||
76 | n,d = (v,1) | ||
77 | return pyexiv2.Rational(int(n), int(d)) | ||
78 | |||
79 | def from_rational(v): | ||
80 | if not v: return v | ||
81 | n,d = str(v).split('/') | ||
82 | if d == '1': | ||
83 | return str(n) | ||
84 | return str(v) | ||
85 | |||
86 | def from_fstop(v): | ||
87 | if '/' in v: | ||
88 | whole, frac = v.split(' ') | ||
89 | n,d = frac.split('/') | ||
90 | if d == '2': scale = HALF_STOP_SCALE | ||
91 | if d == '3': scale = THIRD_STOP_SCALE | ||
92 | i = scale.index(whole) | ||
93 | i += int(n) | ||
94 | f = fractions.Fraction.from_decimal(decimal.Decimal(str(scale[i]))) | ||
95 | return str(f) | ||
96 | f = fractions.Fraction.from_decimal(decimal.Decimal(v)) | ||
97 | return str(f) | ||
98 | |||
99 | def to_fstop(v): | ||
100 | if '/' in v: | ||
101 | n,d = v.split('/') | ||
102 | return str(float(n)/float(d)) | ||
103 | return v | ||
104 | |||
105 | def encode_comments(d, comments): | ||
106 | ret = '' | ||
107 | for k in PRIVATE_KEYS: | ||
108 | if k in d.keys(): | ||
109 | ret += '%s: %s\n' % (k, d[k]) | ||
110 | ret += '\n'+comments | ||
111 | return ret | ||
112 | |||
113 | def decode_comments(comments): | ||
114 | d = {} | ||
115 | ret = '' | ||
116 | lines = comments.split('\n') | ||
117 | while lines: | ||
118 | line = lines.pop(0).strip() | ||
119 | if not line: break | ||
120 | if ':' in line: | ||
121 | k,v = line.split(':', 1) | ||
122 | d[k.strip()] = v.strip() | ||
123 | else: | ||
124 | ret += line+'\n' | ||
125 | break | ||
126 | return d, ret+'\n'.join(lines) | ||
127 | |||
128 | class ExiFilm(object): | ||
129 | |||
130 | def __init__(self): | ||
131 | self.image = None | ||
132 | self.xml = gtk.glade.XML('exifilm.glade', 'main_window') | ||
133 | |||
134 | self.file_combo = self.xml.get_widget('file') | ||
135 | |||
136 | self.id_entry = self.xml.get_widget('id') | ||
137 | self.film_entry = self.xml.get_widget('film') | ||
138 | self.carrier_entry = self.xml.get_widget('carrier') | ||
139 | self.process_entry = self.xml.get_widget('process') | ||
140 | self.lens_entry = self.xml.get_widget('lens') | ||
141 | self.aperture_entry = self.xml.get_widget('aperture') | ||
142 | self.shutter_entry = self.xml.get_widget('shutter') | ||
143 | |||
144 | self.front_button = self.xml.get_widget('front') | ||
145 | self.rear_button = self.xml.get_widget('rear') | ||
146 | |||
147 | self.description_entry = self.xml.get_widget('description') | ||
148 | self.date_button = self.xml.get_widget('date') | ||
149 | |||
150 | self.comments_text = self.xml.get_widget('comments') | ||
151 | self.comments_buffer = gtk.TextBuffer() | ||
152 | self.comments_text.set_buffer(self.comments_buffer) | ||
153 | |||
154 | # Keep the last selected date to provide a sane default | ||
155 | self.lastdate = None | ||
156 | |||
157 | dic = { | ||
158 | 'on_main_window_destroy': self.window_closed, | ||
159 | 'on_main_window_key_press_event': self.key_press, | ||
160 | 'on_date_clicked': self.date_clicked, | ||
161 | 'on_front_clicked': self.front_clicked, | ||
162 | 'on_rear_clicked': self.rear_clicked, | ||
163 | 'on_file_changed': self.file_changed, | ||
164 | } | ||
165 | |||
166 | self.xml.signal_autoconnect (dic) | ||
167 | |||
168 | self.file_store = gtk.ListStore(gobject.TYPE_STRING) | ||
169 | cell = gtk.CellRendererText() | ||
170 | self.file_combo.pack_start(cell, True) | ||
171 | self.file_combo.add_attribute(cell, 'text', 0) | ||
172 | self.file_combo.set_model(self.file_store) | ||
173 | |||
174 | self.filename = None | ||
175 | first = None | ||
176 | self.directory = '.' | ||
177 | if len(sys.argv)>1: | ||
178 | self.directory = sys.argv[1] | ||
179 | files = os.listdir(self.directory) | ||
180 | files.sort() | ||
181 | for fn in files: | ||
182 | if not (fn.lower().endswith('.jpeg') or | ||
183 | fn.lower().endswith('.jpg')): | ||
184 | continue | ||
185 | if not first: first = fn | ||
186 | self.file_store.append((fn,)) | ||
187 | if first: | ||
188 | self.file_combo.set_active(0) | ||
189 | |||
190 | def file_changed(self, widget, data=None): | ||
191 | if self.filename: | ||
192 | self.save() | ||
193 | i = self.file_combo.get_active() | ||
194 | fn = self.file_store[i][0] | ||
195 | self.load(fn) | ||
196 | self.id_entry.grab_focus() | ||
197 | |||
198 | def key_press(self, widget, data=None): | ||
199 | if data.keyval == gtk.keysyms.Page_Up: | ||
200 | i = self.file_combo.get_active() | ||
201 | if i>0: | ||
202 | self.file_combo.set_active(i-1) | ||
203 | return True | ||
204 | |||
205 | if data.keyval == gtk.keysyms.Page_Down: | ||
206 | i = self.file_combo.get_active() | ||
207 | if i<len(self.file_store)-1: | ||
208 | self.file_combo.set_active(i+1) | ||
209 | return True | ||
210 | |||
211 | def load(self, fn): | ||
212 | fn = os.path.join(self.directory, fn) | ||
213 | self.filename = fn | ||
214 | |||
215 | image = pyexiv2.Image(fn) | ||
216 | image.readMetadata() | ||
217 | keys = image.exifKeys() | ||
218 | self.image = image | ||
219 | |||
220 | def get(key, default=''): | ||
221 | if key in keys: | ||
222 | return image[key] | ||
223 | return default | ||
224 | |||
225 | self.date = get('Exif.Photo.DateTimeOriginal', None) | ||
226 | if self.date: | ||
227 | self.date_button.set_label(str(self.date.date())) | ||
228 | else: | ||
229 | self.date_button.set_label('Set') | ||
230 | |||
231 | self.shutter_entry.set_text(from_rational(get('Exif.Photo.ExposureTime'))) | ||
232 | self.aperture_entry.set_text(to_fstop(from_rational(get('Exif.Photo.FNumber')))) | ||
233 | self.lens_entry.set_text(from_rational(get('Exif.Photo.FocalLength'))) | ||
234 | |||
235 | self.description_entry.set_text(get('Exif.Image.ImageDescription')) | ||
236 | extras, comments = decode_comments(get('Exif.Photo.UserComment')) | ||
237 | self.comments_buffer.set_text(comments) | ||
238 | |||
239 | self.id_entry.set_text(extras.get(ID, '')) | ||
240 | self.film_entry.set_text(extras.get(FILM, '')) | ||
241 | self.carrier_entry.set_text(extras.get(CARRIER, '')) | ||
242 | self.process_entry.set_text(extras.get(PROCESS, '')) | ||
243 | |||
244 | self.front_movements = extras.get(FRONT_MOVEMENTS, '') | ||
245 | if self.front_movements: | ||
246 | self.front_button.set_label(self.front_movements) | ||
247 | else: | ||
248 | self.front_button.set_label('None') | ||
249 | |||
250 | self.rear_movements = extras.get(REAR_MOVEMENTS, '') | ||
251 | if self.rear_movements: | ||
252 | self.rear_button.set_label(self.rear_movements) | ||
253 | else: | ||
254 | self.rear_button.set_label('None') | ||
255 | |||
256 | def save(self): | ||
257 | if self.date: | ||
258 | self.image['Exif.Photo.DateTimeOriginal'] = self.date | ||
259 | v = self.shutter_entry.get_text() | ||
260 | if v: self.image['Exif.Photo.ExposureTime'] = to_rational(v) | ||
261 | v = self.aperture_entry.get_text() | ||
262 | if v: self.image['Exif.Photo.FNumber'] = to_rational(from_fstop(v)) | ||
263 | v = self.lens_entry.get_text() | ||
264 | if v: self.image['Exif.Photo.FocalLength'] = to_rational(v) | ||
265 | v = self.description_entry.get_text() | ||
266 | if v: self.image['Exif.Image.ImageDescription'] = v | ||
267 | |||
268 | extras = {} | ||
269 | |||
270 | v = self.id_entry.get_text() | ||
271 | if v: extras[ID] = v | ||
272 | v = self.film_entry.get_text() | ||
273 | if v: | ||
274 | extras[FILM] = v | ||
275 | m = ISO_RE.search(v) | ||
276 | if m: | ||
277 | iso = int(m.group(0)) | ||
278 | self.image['Exif.Photo.ISOSpeedRatings'] = iso | ||
279 | v = self.carrier_entry.get_text() | ||
280 | if v: extras[CARRIER] = v | ||
281 | v = self.process_entry.get_text() | ||
282 | if v: extras[PROCESS] = v | ||
283 | if self.front_movements: | ||
284 | extras[FRONT_MOVEMENTS] = self.front_movements | ||
285 | if self.rear_movements: | ||
286 | extras[REAR_MOVEMENTS] = self.rear_movements | ||
287 | |||
288 | bounds = self.comments_buffer.get_bounds() | ||
289 | v = self.comments_buffer.get_text(bounds[0], bounds[1]) | ||
290 | if v or extras: | ||
291 | self.image['Exif.Photo.UserComment'] = encode_comments(extras, v) | ||
292 | |||
293 | self.image.writeMetadata() | ||
294 | |||
295 | def window_closed(self, widget, data=None): | ||
296 | if self.image: | ||
297 | self.save() | ||
298 | gtk.main_quit() | ||
299 | |||
300 | def date_clicked(self, widget, data=None): | ||
301 | xml = gtk.glade.XML('exifilm.glade', 'calendar_dialog') | ||
302 | calendar_dialog = xml.get_widget('calendar_dialog') | ||
303 | calendar = xml.get_widget('calendar') | ||
304 | if self.date: | ||
305 | date = self.date | ||
306 | else: | ||
307 | if self.lastdate: | ||
308 | date = self.lastdate | ||
309 | else: | ||
310 | date = datetime.datetime.now() | ||
311 | calendar.select_month(date.month-1, date.year) | ||
312 | calendar.select_day(date.day) | ||
313 | r = calendar_dialog.run() | ||
314 | if r: | ||
315 | date = calendar.get_date() | ||
316 | self.date = datetime.datetime(date[0], date[1]+1, date[2]) | ||
317 | self.lastdate = self.date | ||
318 | self.date_button.set_label(str(self.date.date())) | ||
319 | calendar_dialog.destroy() | ||
320 | |||
321 | def front_clicked(self, widget, data=None): | ||
322 | moves = self.front_movements.split('/') | ||
323 | moves = self.get_movements(moves) | ||
324 | self.front_movements = '/'.join(moves) | ||
325 | if self.front_movements: | ||
326 | self.front_button.set_label(self.front_movements) | ||
327 | else: | ||
328 | self.front_button.set_label('None') | ||
329 | |||
330 | def rear_clicked(self, widget, data=None): | ||
331 | moves = self.rear_movements.split('/') | ||
332 | moves = self.get_movements(moves) | ||
333 | self.rear_movements = '/'.join(moves) | ||
334 | if self.rear_movements: | ||
335 | self.rear_button.set_label(self.rear_movements) | ||
336 | else: | ||
337 | self.rear_button.set_label('None') | ||
338 | |||
339 | def get_movements(self, orig_movements): | ||
340 | xml = gtk.glade.XML('exifilm.glade', 'movement_dialog') | ||
341 | dialog = xml.get_widget('movement_dialog') | ||
342 | tree_view = xml.get_widget('movements') | ||
343 | |||
344 | column = gtk.TreeViewColumn("Movements") | ||
345 | renderer=gtk.CellRendererText() | ||
346 | column.pack_start(renderer,0) | ||
347 | column.add_attribute(renderer, 'text', 0) | ||
348 | tree_view.append_column(column) | ||
349 | |||
350 | tree_store = gtk.TreeStore(str) | ||
351 | tree_view.set_model(tree_store) | ||
352 | tree_view.get_selection().set_mode(gtk.SELECTION_MULTIPLE) | ||
353 | for i,m in enumerate(CAMERA_MOVEMENTS): | ||
354 | tree_store.append(None, (m,)) | ||
355 | if m in orig_movements: | ||
356 | tree_view.get_selection().select_path((i,)) | ||
357 | |||
358 | r = dialog.run() | ||
359 | if r: | ||
360 | store, rows = tree_view.get_selection().get_selected_rows() | ||
361 | ret = [] | ||
362 | for row in rows: | ||
363 | ret.append(tree_store.get_value(tree_store.get_iter(row), 0)) | ||
364 | else: | ||
365 | ret = orig_movements | ||
366 | dialog.destroy() | ||
367 | return ret | ||
368 | |||
369 | def main(): | ||
370 | gdk.threads_init() | ||
371 | gdk.threads_enter() | ||
372 | ExiFilm() | ||
373 | gtk.main() | ||
374 | gdk.threads_leave() | ||
375 | |||
376 | if __name__=='__main__': | ||
377 | if len(sys.argv)>1 and sys.argv[1][0]=='-': | ||
378 | print "Usage: %s [PATH]" % sys.argv[0] | ||
379 | |||
380 | print " PATH is a directory with JPEG files to edit." | ||
381 | print " PATH defaults to the current directory." | ||
382 | else: | ||
383 | main() | ||
diff --git a/lfrecord.ps b/lfrecord.ps new file mode 100644 index 0000000..23153c1 --- /dev/null +++ b/lfrecord.ps | |||
@@ -0,0 +1,781 @@ | |||
1 | %!PS-Adobe-3.0 | ||
2 | %%Pages: 1 | ||
3 | %%BoundingBox: 0 0 612 792 | ||
4 | %%EndComments | ||
5 | %%Page: 1 1 | ||
6 | |||
7 | % ExiFilm -- Add film exposure metadata to EXIF tags of digital images | ||
8 | % Copyright (C) 2009 James E. Blair <corvus@gnu.org> | ||
9 | % | ||
10 | % This program is free software: you can redistribute it and/or modify | ||
11 | % it under the terms of the GNU General Public License as published by | ||
12 | % the Free Software Foundation, either version 3 of the License, or | ||
13 | % (at your option) any later version. | ||
14 | % | ||
15 | % This program is distributed in the hope that it will be useful, | ||
16 | % but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
17 | % MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
18 | % GNU General Public License for more details. | ||
19 | % | ||
20 | % You should have received a copy of the GNU General Public License | ||
21 | % along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
22 | |||
23 | % User servicable: | ||
24 | |||
25 | /in { 72 mul } def | ||
26 | |||
27 | /cellheight 12.75 def | ||
28 | /plantop 9.75 in def % 8.5 - .5 in at top | ||
29 | /planleft 7 32 div in def | ||
30 | /planwidth 3 in 15 16 div in add def | ||
31 | |||
32 | % 3 15/16 in wide | ||
33 | % 5 in high | ||
34 | |||
35 | /normalfont {/Times-Roman 10 selectfont} def | ||
36 | /smallfont {/Times-Roman 8 selectfont} def | ||
37 | |||
38 | /baselineskip 12 def | ||
39 | 1 setlinewidth | ||
40 | |||
41 | % Less user servicable: | ||
42 | |||
43 | /planheight 21 cellheight mul def | ||
44 | /condtop plantop planheight sub def | ||
45 | /condleft planleft def | ||
46 | /condheight 11 cellheight mul def | ||
47 | |||
48 | /cell {/cury curx cury wd cellht box def} def | ||
49 | /cell1 {curx cury wd1 cellht box pop} def | ||
50 | /cell2cr {/cury curx wd1 add cury wd2 cellht box def} def | ||
51 | /cell3cr {/cury curx wd1 add wd2 add cury wd3 cellht box def} def | ||
52 | /cell2 {curx wd1 add cury wd2 cellht box pop} def | ||
53 | /cell3 {curx wd1 add wd2 add cury wd3 cellht box pop} def | ||
54 | /triangle {newpath curx cury moveto 6 0 cellht 2 div sub rlineto | ||
55 | -6 0 cellht 2 div sub rlineto closepath fill} def | ||
56 | |||
57 | |||
58 | /toppic | ||
59 | { | ||
60 | 0 18 translate | ||
61 | 0.8 -0.8 scale | ||
62 | 0 0 0 setrgbcolor | ||
63 | [] 0 setdash | ||
64 | 1 setlinewidth | ||
65 | 0 setlinejoin | ||
66 | 0 setlinecap | ||
67 | gsave [1 0 0 1 0 0] concat | ||
68 | 0 0 0 setrgbcolor | ||
69 | [] 0 setdash | ||
70 | 0.625 setlinewidth | ||
71 | 1 setlinejoin | ||
72 | 1 setlinecap | ||
73 | newpath | ||
74 | 17.465566 7.6270604 moveto | ||
75 | 17.34201 7.4607341 17.023642 7.1667431 16.801411 7.0511098 curveto | ||
76 | 16.503644 6.896187 16.307292 6.8516095 16.026569 6.7055509 curveto | ||
77 | 15.791517 6.5832505 15.419851 6.5327667 15.14103 6.5327667 curveto | ||
78 | 14.851109 6.5327667 14.510791 6.4751688 14.200137 6.4751688 curveto | ||
79 | 13.906717 6.4751688 13.544314 6.6414571 13.314598 6.8207372 curveto | ||
80 | 13.068846 7.0125432 12.874548 7.2361726 12.595099 7.4542762 curveto | ||
81 | 12.344743 7.6496678 12.125565 7.8753705 11.930944 8.1454035 curveto | ||
82 | 11.751845 8.3938944 11.61173 8.7253772 11.543518 9.0093151 curveto | ||
83 | 11.483134 9.2606497 11.432821 9.6008921 11.432821 9.9308246 curveto | ||
84 | 11.432821 10.284991 11.481859 10.646709 11.543518 10.96752 curveto | ||
85 | 11.606347 11.294419 11.689348 11.459357 11.764903 11.773844 curveto | ||
86 | 11.826229 12.029125 12.085382 12.337715 12.207673 12.464971 curveto | ||
87 | 12.411225 12.676797 12.681981 12.913342 12.927172 13.040921 curveto | ||
88 | 13.208038 13.187056 13.356056 13.321654 13.591326 13.444078 curveto | ||
89 | 13.894704 13.60193 14.210656 13.770986 14.532219 13.904833 curveto | ||
90 | 14.799874 14.016243 15.064115 14.020019 15.362414 14.020019 curveto | ||
91 | 15.668037 14.020019 15.886968 14.041942 16.1926 13.962421 curveto | ||
92 | 16.488636 13.885412 16.686938 13.733028 16.912108 13.674451 curveto | ||
93 | 17.175607 13.605906 17.382184 13.372271 17.576263 13.271294 curveto | ||
94 | 17.802565 13.15354 17.966257 13.038239 18.12972 12.868137 curveto | ||
95 | 18.33059 12.659107 18.448373 12.636072 18.517146 12.349785 curveto | ||
96 | 18.58201 12.07978 18.683187 12.005006 18.683187 11.658657 curveto | ||
97 | 18.683187 11.370687 18.683187 11.082707 18.683187 10.794746 curveto | ||
98 | 18.683187 10.482732 18.689036 10.243133 18.627843 9.9884225 curveto | ||
99 | 18.56315 9.7191599 18.57249 9.4050915 18.57249 9.1245109 curveto | ||
100 | 18.57249 8.8389752 18.46301 8.6086787 18.351105 8.3757857 curveto | ||
101 | 18.246685 8.158462 18.001799 8.0698776 17.852991 7.9150309 curveto | ||
102 | 17.675889 7.730729 17.748724 7.7007222 17.465566 7.6270604 curveto | ||
103 | closepath | ||
104 | stroke | ||
105 | 0 0 0 setrgbcolor | ||
106 | [] 0 setdash | ||
107 | 0.625 setlinewidth | ||
108 | 1 setlinejoin | ||
109 | 1 setlinecap | ||
110 | newpath | ||
111 | 18.908969 9.1187484 moveto | ||
112 | 19.132586 9.2148318 19.670178 9.5204546 19.889559 9.6723899 curveto | ||
113 | 20.225854 9.9053021 20.525329 9.9224118 20.835946 10.076851 curveto | ||
114 | 21.210027 10.262847 21.490107 10.364636 21.849811 10.465301 curveto | ||
115 | 22.38606 10.615383 21.920523 10.684453 21.563764 10.76915 curveto | ||
116 | 21.276372 10.837386 20.927903 10.920113 20.619207 10.993399 curveto | ||
117 | 20.270784 11.076118 19.970536 11.147404 19.607192 11.233666 curveto | ||
118 | 19.449759 11.271042 19.292336 11.308417 19.134913 11.345791 curveto | ||
119 | stroke | ||
120 | 0 0 0 setrgbcolor | ||
121 | [] 0 setdash | ||
122 | 0.625 setlinewidth | ||
123 | 1 setlinejoin | ||
124 | 1 setlinecap | ||
125 | newpath | ||
126 | 12.479003 7.3178906 moveto | ||
127 | 12.297483 7.2051594 10.437915 6.743884 10.199405 6.6961819 curveto | ||
128 | 9.9461844 6.6455378 8.2389814 6.412102 8.4897064 6.4371367 curveto | ||
129 | 8.9210134 6.4802021 7.6023054 6.3853275 7.3499064 6.3853275 curveto | ||
130 | 7.1865764 6.3853275 6.6748094 6.3424179 6.2101074 6.3853275 curveto | ||
131 | 5.9802984 6.4065477 4.6730454 6.5580544 4.3967904 6.6961819 curveto | ||
132 | 4.1597714 6.8146914 3.9322444 6.8766459 3.6714644 7.0070363 curveto | ||
133 | 3.3812444 7.1521462 3.1878204 7.2920552 2.9461374 7.4733178 curveto | ||
134 | 2.7386724 7.6289163 2.4671594 7.8455027 2.2726194 7.9914084 curveto | ||
135 | 2.0299164 8.1734353 1.8916084 8.3206101 1.7027194 8.5094989 curveto | ||
136 | 1.5052674 8.706951 1.4151344 8.8256235 1.2882464 9.0793985 curveto | ||
137 | 1.1595274 9.3368386 1.0339524 9.4843697 0.92558337 9.7011073 curveto | ||
138 | 0.78229837 9.9876779 0.64040737 10.116486 0.56292037 10.426434 curveto | ||
139 | 0.50396737 10.662246 0.51591437 10.873501 0.45930237 11.099952 curveto | ||
140 | 0.39136637 11.371693 0.56233537 11.565062 0.66653837 11.77347 curveto | ||
141 | 0.76972037 11.979834 1.0569594 12.231766 1.1846294 12.395178 curveto | ||
142 | 1.4171204 12.692756 1.6462124 12.974507 1.9099554 13.172314 curveto | ||
143 | 2.2042814 13.393059 2.9527384 13.952751 3.2569914 14.104877 curveto | ||
144 | 4.1361764 14.565305 4.7738594 14.88324 5.7438264 14.985631 curveto | ||
145 | 6.1202154 15.079729 7.3525084 15.363749 8.8005604 15.192867 curveto | ||
146 | 9.8815834 15.065298 10.824802 14.750645 11.494631 14.260304 curveto | ||
147 | 12.29744 13.766723 12.403624 13.534597 12.789858 13.120505 curveto | ||
148 | stroke | ||
149 | grestore | ||
150 | } def | ||
151 | |||
152 | /sidepic | ||
153 | { | ||
154 | 0 18 translate | ||
155 | 0.8 -0.8 scale | ||
156 | 0 0 0 setrgbcolor | ||
157 | [] 0 setdash | ||
158 | 1 setlinewidth | ||
159 | 0 setlinejoin | ||
160 | 0 setlinecap | ||
161 | gsave [1 0 0 1 0 0] concat | ||
162 | 0 0 0 setrgbcolor | ||
163 | [] 0 setdash | ||
164 | 0.625 setlinewidth | ||
165 | 1 setlinejoin | ||
166 | 1 setlinecap | ||
167 | newpath | ||
168 | 17.41745 3.3235764 moveto | ||
169 | 17.28754 3.1486964 16.9528 2.8395864 16.71914 2.7180064 curveto | ||
170 | 16.40606 2.5551164 16.19961 2.5082464 15.90445 2.3546764 curveto | ||
171 | 15.65731 2.2260864 15.26653 2.1730064 14.97337 2.1730064 curveto | ||
172 | 14.66854 2.1730064 14.31072 2.1124464 13.98409 2.1124464 curveto | ||
173 | 13.67558 2.1124464 13.29454 2.2872864 13.05301 2.4757864 curveto | ||
174 | 12.79462 2.6774564 12.59033 2.9125864 12.296511 3.1419064 curveto | ||
175 | 12.033281 3.3473464 11.802831 3.5846564 11.598201 3.8685764 curveto | ||
176 | 11.409891 4.1298464 11.262571 4.4783764 11.190851 4.7769164 curveto | ||
177 | 11.127361 5.0411764 11.074461 5.3989164 11.074461 5.7458164 curveto | ||
178 | 11.074461 6.1181964 11.126021 6.4985164 11.190851 6.8358264 curveto | ||
179 | 11.256911 7.1795364 11.344181 7.3529564 11.423621 7.6836164 curveto | ||
180 | 11.488101 7.9520264 11.760581 8.2764864 11.889161 8.4102864 curveto | ||
181 | 12.103181 8.6330064 12.387861 8.8817164 12.64566 9.0158564 curveto | ||
182 | 12.94097 9.1695064 13.0966 9.3110264 13.34397 9.4397464 curveto | ||
183 | 13.66295 9.6057164 13.99515 9.7834664 14.33325 9.9241964 curveto | ||
184 | 14.61467 10.041336 14.8925 10.045306 15.20614 10.045306 curveto | ||
185 | 15.52748 10.045306 15.75767 10.068356 16.07902 9.9847464 curveto | ||
186 | 16.39028 9.9037764 16.59878 9.7435564 16.83553 9.6819664 curveto | ||
187 | 17.11258 9.6098964 17.32978 9.3642464 17.53384 9.2580764 curveto | ||
188 | 17.77178 9.1342664 17.94389 9.0130364 18.11576 8.8341864 curveto | ||
189 | 18.32696 8.6144064 18.4508 8.5901864 18.52311 8.2891764 curveto | ||
190 | 18.59131 8.0052864 18.69769 7.9266664 18.69769 7.5625064 curveto | ||
191 | 18.69769 7.2597264 18.69769 6.9569364 18.69769 6.6541664 curveto | ||
192 | 18.69769 6.3261064 18.70384 6.0741864 18.6395 5.8063764 curveto | ||
193 | 18.57148 5.5232664 18.5813 5.1930464 18.5813 4.8980364 curveto | ||
194 | 18.5813 4.5978164 18.46619 4.3556764 18.34853 4.1108064 curveto | ||
195 | 18.23874 3.8823064 17.98126 3.7891664 17.8248 3.6263564 curveto | ||
196 | 17.63859 3.4325764 17.71517 3.4010264 17.41745 3.3235764 curveto | ||
197 | closepath | ||
198 | stroke | ||
199 | 0 0 0 setrgbcolor | ||
200 | [] 0 setdash | ||
201 | 0.625 setlinewidth | ||
202 | 1 setlinejoin | ||
203 | 1 setlinecap | ||
204 | newpath | ||
205 | 18.94656 5.9379964 moveto | ||
206 | 19.1584 6.0815564 19.65288 6.5037464 19.84927 6.7041364 curveto | ||
207 | 20.15032 7.0113264 20.45615 7.0883864 20.74625 7.3094564 curveto | ||
208 | 21.09562 7.5756964 21.36463 7.7363464 21.716081 7.9116264 curveto | ||
209 | 22.240021 8.1729464 21.745631 8.1519364 21.36046 8.1686364 curveto | ||
210 | 21.05018 8.1820964 20.67396 8.1984064 20.34068 8.2128564 curveto | ||
211 | 19.96451 8.2291664 19.64035 8.2432264 19.24807 8.2602364 curveto | ||
212 | 19.0781 8.2676064 18.90814 8.2749764 18.73818 8.2823464 curveto | ||
213 | stroke | ||
214 | 0 0 0 setrgbcolor | ||
215 | [] 0 setdash | ||
216 | 0.625 setlinewidth | ||
217 | 1 setlinejoin | ||
218 | 1 setlinecap | ||
219 | newpath | ||
220 | 11.058081 6.3609964 moveto | ||
221 | 10.898991 6.3609964 10.297991 6.3609964 9.9236506 6.3609964 curveto | ||
222 | 9.6528706 6.3609964 9.2296906 6.4606964 9.0019306 6.5275864 curveto | ||
223 | 8.6792106 6.6223764 8.3901106 6.6031664 8.0802106 6.6941864 curveto | ||
224 | 7.7549906 6.7896964 7.3425006 6.8692064 7.0875806 6.9440764 curveto | ||
225 | 6.7203606 7.0519264 6.3784006 7.1731864 6.0240506 7.2772664 curveto | ||
226 | 5.6876206 7.3760764 5.4495006 7.5314764 5.1732306 7.6937564 curveto | ||
227 | 4.8089906 7.9077164 4.5570206 8.1390264 4.1806106 8.3601364 curveto | ||
228 | 3.8315206 8.5651864 3.5054206 9.0700664 3.2588806 9.3597064 curveto | ||
229 | 2.9162706 9.7622164 2.6772606 10.143226 2.4789706 10.609166 curveto | ||
230 | 2.2757806 11.086586 2.1067606 11.567026 1.9117506 12.025216 curveto | ||
231 | 1.7229306 12.468886 1.5183906 12.957456 1.4154406 13.441276 curveto | ||
232 | 1.3145406 13.915446 1.0273606 14.353136 0.84822058 14.774036 curveto | ||
233 | 0.65579058 15.226186 0.63552058 15.643266 0.63552058 15.773606 curveto | ||
234 | stroke | ||
235 | 0 0 0 setrgbcolor | ||
236 | [] 0 setdash | ||
237 | 0.625 setlinewidth | ||
238 | 1 setlinejoin | ||
239 | 1 setlinecap | ||
240 | newpath | ||
241 | 14.33933 10.302876 moveto | ||
242 | 14.20693 10.595156 14.14423 11.072806 13.90194 11.429396 curveto | ||
243 | 13.70442 11.720106 13.37015 12.016406 13.17297 12.234056 curveto | ||
244 | 12.88897 12.547546 12.59356 12.873636 12.298201 13.199656 curveto | ||
245 | 12.020021 13.506716 11.823431 13.804186 11.496341 14.165246 curveto | ||
246 | 11.169801 14.525686 10.912571 14.749106 10.548671 15.050376 curveto | ||
247 | 10.232431 15.312176 9.7936806 15.426826 9.4552106 15.613636 curveto | ||
248 | 9.1243106 15.796266 8.5739906 15.756236 8.2159606 15.855036 curveto | ||
249 | 7.8258106 15.962696 7.3481706 15.832996 6.9767106 15.935496 curveto | ||
250 | 6.5954506 16.040716 6.0587306 15.935496 5.6645506 15.935496 curveto | ||
251 | 5.2171706 15.935496 4.8659706 16.015966 4.4253006 16.015966 curveto | ||
252 | 4.0136906 16.015966 3.5635006 15.935496 3.1131506 15.935496 curveto | ||
253 | 2.7207406 15.935496 2.2370206 15.733586 2.0196906 15.613636 curveto | ||
254 | 1.7663706 15.473826 1.1338906 15.325916 1.0720306 15.291776 curveto | ||
255 | stroke | ||
256 | 0 0 0 setrgbcolor | ||
257 | [] 0 setdash | ||
258 | 0.63630593 setlinewidth | ||
259 | 1 setlinejoin | ||
260 | 1 setlinecap | ||
261 | newpath | ||
262 | 9.9264619 15.524615 moveto | ||
263 | 9.601864 15.336485 9.9988871 16.363201 9.9988871 16.783897 curveto | ||
264 | 9.9988871 17.343824 9.8991612 17.884929 9.9988871 18.462927 curveto | ||
265 | 10.104136 19.072974 9.9702746 19.353219 10.288574 19.722199 curveto | ||
266 | 10.538501 20.011916 10.948726 20.272725 11.157634 20.393812 curveto | ||
267 | 11.29979 20.476203 11.505777 20.474522 11.519735 20.477757 curveto | ||
268 | stroke | ||
269 | 0 0 0 setrgbcolor | ||
270 | [] 0 setdash | ||
271 | 0.625 setlinewidth | ||
272 | 1 setlinejoin | ||
273 | 1 setlinecap | ||
274 | newpath | ||
275 | 10.213238 19.68757 moveto | ||
276 | 10.382008 19.78072 9.6081369 20.54456 9.4113669 20.65317 curveto | ||
277 | 9.2846369 20.72311 9.1736069 20.82462 9.0468769 20.89457 curveto | ||
278 | stroke | ||
279 | 0 0 0 setrgbcolor | ||
280 | [] 0 setdash | ||
281 | 0.625 setlinewidth | ||
282 | 1 setlinejoin | ||
283 | 1 setlinecap | ||
284 | newpath | ||
285 | 6.5393206 16.015966 moveto | ||
286 | 6.2133206 16.195896 6.5393206 16.820626 6.5393206 17.222956 curveto | ||
287 | 6.5393206 17.627916 6.5393206 17.996046 6.5393206 18.429956 curveto | ||
288 | 6.5393206 18.885926 6.5393206 19.341896 6.5393206 19.797876 curveto | ||
289 | 6.5393206 19.821846 7.2722806 20.242636 7.3411906 20.280676 curveto | ||
290 | 7.3483106 20.418036 7.4383906 20.334316 7.4869906 20.361136 curveto | ||
291 | stroke | ||
292 | 0 0 0 setrgbcolor | ||
293 | [] 0 setdash | ||
294 | 0.625 setlinewidth | ||
295 | 1 setlinejoin | ||
296 | 1 setlinecap | ||
297 | newpath | ||
298 | 6.5393206 19.797876 moveto | ||
299 | 6.8774206 19.984476 6.0047406 20.387956 5.7374506 20.683006 curveto | ||
300 | 5.6645606 20.763466 5.5916606 20.843936 5.5187606 20.924396 curveto | ||
301 | stroke | ||
302 | gsave | ||
303 | 0 0 0 setrgbcolor | ||
304 | newpath | ||
305 | 16.59914 4.9921064 moveto | ||
306 | 16.75393 5.5208564 16.53852 5.6023764 16.16176 5.3944364 curveto | ||
307 | 15.78595 5.1870264 16.27681 4.8497864 16.59914 4.9921064 curveto | ||
308 | closepath | ||
309 | fill | ||
310 | grestore | ||
311 | 0 0 0 setrgbcolor | ||
312 | [] 0 setdash | ||
313 | 0.625 setlinewidth | ||
314 | 1 setlinejoin | ||
315 | 1 setlinecap | ||
316 | newpath | ||
317 | 16.59914 4.9921064 moveto | ||
318 | 16.75393 5.5208564 16.53852 5.6023764 16.16176 5.3944364 curveto | ||
319 | 15.78595 5.1870264 16.27681 4.8497864 16.59914 4.9921064 curveto | ||
320 | closepath | ||
321 | stroke | ||
322 | grestore | ||
323 | } def | ||
324 | |||
325 | /greybox | ||
326 | { | ||
327 | /height exch def | ||
328 | /width exch def | ||
329 | /top exch def | ||
330 | /left exch def | ||
331 | |||
332 | /bottom top height sub def | ||
333 | |||
334 | .8 .8 .8 setrgbcolor | ||
335 | left bottom width height rectfill | ||
336 | 0 0 0 setrgbcolor | ||
337 | left bottom width height rectstroke | ||
338 | bottom | ||
339 | } def | ||
340 | |||
341 | /blackbox | ||
342 | { | ||
343 | /height exch def | ||
344 | /width exch def | ||
345 | /top exch def | ||
346 | /left exch def | ||
347 | |||
348 | /bottom top height sub def | ||
349 | |||
350 | 0 0 0 setrgbcolor | ||
351 | left bottom width height rectfill | ||
352 | left bottom width height rectstroke | ||
353 | bottom | ||
354 | } def | ||
355 | |||
356 | /box | ||
357 | { | ||
358 | /height exch def | ||
359 | /width exch def | ||
360 | /top exch def | ||
361 | /left exch def | ||
362 | |||
363 | /bottom top height sub def | ||
364 | |||
365 | 0 0 0 setrgbcolor | ||
366 | left bottom width height rectstroke | ||
367 | bottom | ||
368 | } def | ||
369 | |||
370 | /writingline | ||
371 | { | ||
372 | /height exch def | ||
373 | /width exch def | ||
374 | /top exch def | ||
375 | /left exch def | ||
376 | |||
377 | /bottom top height sub def | ||
378 | |||
379 | .125 setlinewidth | ||
380 | left bottom moveto width 0 rlineto stroke | ||
381 | 1 setlinewidth | ||
382 | bottom | ||
383 | } def | ||
384 | |||
385 | |||
386 | /centertext | ||
387 | { | ||
388 | /s exch def | ||
389 | /x2 exch def | ||
390 | /x1 exch def | ||
391 | /y exch def | ||
392 | |||
393 | x2 x1 sub 2 div x1 add % midpoint | ||
394 | s stringwidth pop 2 div % half the string width | ||
395 | sub % move left to start | ||
396 | |||
397 | y baselineskip sub moveto s show | ||
398 | y baselineskip sub | ||
399 | } def | ||
400 | |||
401 | /righttext | ||
402 | { | ||
403 | /s exch def | ||
404 | /x2 exch def | ||
405 | /x1 exch def | ||
406 | /y exch def | ||
407 | |||
408 | x2 | ||
409 | s stringwidth pop | ||
410 | sub 1 sub | ||
411 | |||
412 | y baselineskip sub moveto s show | ||
413 | y baselineskip sub | ||
414 | } def | ||
415 | |||
416 | /lefttext | ||
417 | { | ||
418 | /s exch def | ||
419 | /x2 exch def | ||
420 | /x1 exch def | ||
421 | /y exch def | ||
422 | |||
423 | x1 1 add | ||
424 | |||
425 | y baselineskip sub moveto s show | ||
426 | y baselineskip sub | ||
427 | } def | ||
428 | |||
429 | |||
430 | /picid | ||
431 | { | ||
432 | /cury exch def | ||
433 | /curx exch def | ||
434 | /wd 42 def | ||
435 | /headht 1 cellheight mul def | ||
436 | /cellht 2 cellheight mul def | ||
437 | |||
438 | curx cury wd headht greybox | ||
439 | |||
440 | cury 2 add | ||
441 | curx curx wd add (ID) centertext | ||
442 | pop | ||
443 | |||
444 | /cury exch def % add height change from box | ||
445 | |||
446 | cell | ||
447 | |||
448 | xpos wd add | ||
449 | } def | ||
450 | |||
451 | /aperture | ||
452 | { | ||
453 | /cury exch def | ||
454 | /curx exch def | ||
455 | /wd 68 def | ||
456 | /headht 1 cellheight mul def | ||
457 | /cellht 2 cellheight mul def | ||
458 | |||
459 | curx cury wd headht greybox | ||
460 | |||
461 | cury 2 add | ||
462 | curx curx wd add (Aperture (f/x)) centertext | ||
463 | pop | ||
464 | |||
465 | /cury exch def % add height change from box | ||
466 | |||
467 | cell | ||
468 | |||
469 | xpos wd add | ||
470 | } def | ||
471 | |||
472 | /shutter | ||
473 | { | ||
474 | /cury exch def | ||
475 | /curx exch def | ||
476 | /wd 68 def | ||
477 | /headht 1 cellheight mul def | ||
478 | /cellht 2 cellheight mul def | ||
479 | |||
480 | curx cury wd headht greybox | ||
481 | |||
482 | cury 2 add | ||
483 | curx curx wd add (Shutter (sec)) centertext | ||
484 | pop | ||
485 | |||
486 | /cury exch def % add height change from box | ||
487 | |||
488 | cell | ||
489 | |||
490 | xpos wd add | ||
491 | } def | ||
492 | |||
493 | /geometry | ||
494 | { | ||
495 | /cury exch def | ||
496 | /curx exch def | ||
497 | /wd 74 def | ||
498 | /headht 1 cellheight mul def | ||
499 | /cellht 2.5 cellheight mul def | ||
500 | |||
501 | curx cury wd headht greybox | ||
502 | |||
503 | cury 2 add | ||
504 | curx curx wd add (Geometry) centertext | ||
505 | pop | ||
506 | |||
507 | /cury exch def % add height change from box | ||
508 | |||
509 | cell | ||
510 | |||
511 | gsave curx 3 add cury 6 add translate toppic grestore | ||
512 | |||
513 | cell | ||
514 | |||
515 | gsave curx 3 add cury 6 add translate sidepic grestore | ||
516 | |||
517 | xpos wd add | ||
518 | } def | ||
519 | |||
520 | /film | ||
521 | { | ||
522 | /cury exch def | ||
523 | /curx exch def | ||
524 | /wd 52 def | ||
525 | /headht 1 cellheight mul def | ||
526 | /cellht 2 cellheight mul def | ||
527 | |||
528 | curx cury wd headht greybox | ||
529 | |||
530 | cury 2 add | ||
531 | curx curx wd add (Film) centertext | ||
532 | pop | ||
533 | |||
534 | /cury exch def % add height change from box | ||
535 | |||
536 | cell | ||
537 | |||
538 | xpos wd add | ||
539 | } def | ||
540 | |||
541 | /carrier | ||
542 | { | ||
543 | /cury exch def | ||
544 | /curx exch def | ||
545 | /wd 42 def | ||
546 | /headht 1 cellheight mul def | ||
547 | /cellht 2 cellheight mul def | ||
548 | |||
549 | curx cury wd headht greybox | ||
550 | |||
551 | cury 2 add | ||
552 | curx curx wd add (Carrier) centertext | ||
553 | pop | ||
554 | |||
555 | /cury exch def % add height change from box | ||
556 | |||
557 | cell | ||
558 | |||
559 | xpos wd add | ||
560 | } def | ||
561 | |||
562 | /lens | ||
563 | { | ||
564 | /cury exch def | ||
565 | /curx exch def | ||
566 | /wd 42 def | ||
567 | /headht 1 cellheight mul def | ||
568 | /cellht 2 cellheight mul def | ||
569 | |||
570 | curx cury wd headht greybox | ||
571 | |||
572 | cury 2 add | ||
573 | curx curx wd add (Lens) centertext | ||
574 | pop | ||
575 | |||
576 | /cury exch def % add height change from box | ||
577 | |||
578 | cell | ||
579 | |||
580 | xpos wd add | ||
581 | } def | ||
582 | |||
583 | /process | ||
584 | { | ||
585 | /cury exch def | ||
586 | /curx exch def | ||
587 | /wd 42 def | ||
588 | /headht 1 cellheight mul def | ||
589 | /cellht 2 cellheight mul def | ||
590 | |||
591 | curx cury wd headht greybox | ||
592 | |||
593 | cury 2 add | ||
594 | curx curx wd add (Process) centertext | ||
595 | pop | ||
596 | |||
597 | /cury exch def % add height change from box | ||
598 | |||
599 | cell | ||
600 | |||
601 | xpos wd add | ||
602 | } def | ||
603 | |||
604 | /date | ||
605 | { | ||
606 | /cury exch def | ||
607 | /curx exch def | ||
608 | |||
609 | /wd 252 108 sub def | ||
610 | /cellht 1.5 cellheight mul def | ||
611 | |||
612 | curx cury wd 2 cellht mul box pop | ||
613 | |||
614 | /cury curx cury wd cellht writingline def | ||
615 | /cury curx cury wd cellht writingline def | ||
616 | |||
617 | /cury cury 2 cellht mul add def | ||
618 | /curx curx wd add def | ||
619 | |||
620 | /wd 108 def | ||
621 | /headht 1 cellheight mul def | ||
622 | /cellht 2 cellheight mul def | ||
623 | |||
624 | curx cury wd headht greybox | ||
625 | |||
626 | cury 2 add | ||
627 | curx curx wd add (Date) centertext | ||
628 | pop | ||
629 | |||
630 | /cury exch def % add height change from box | ||
631 | |||
632 | cell | ||
633 | |||
634 | % draw the writing lines | ||
635 | |||
636 | xpos | ||
637 | } def | ||
638 | |||
639 | /notes | ||
640 | { | ||
641 | /cury exch def | ||
642 | /curx exch def | ||
643 | /wd 252 def | ||
644 | %/headht 1 cellheight mul def | ||
645 | /cellht 1.5 cellheight mul def | ||
646 | /boxht 4.5 in 6 cellheight mul sub def % 5in - header so far | ||
647 | |||
648 | %curx cury wd headht greybox | ||
649 | |||
650 | %cury 2 add | ||
651 | %curx curx wd add (Process) centertext | ||
652 | %pop | ||
653 | |||
654 | %/cury exch def % add height change from box | ||
655 | |||
656 | curx cury wd boxht box pop | ||
657 | |||
658 | %/cury curx 10 add cury wd 20 sub cellht writingline def | ||
659 | |||
660 | /cury curx cury wd cellht writingline def | ||
661 | /cury curx cury wd cellht writingline def | ||
662 | /cury curx cury wd cellht writingline def | ||
663 | /cury curx cury wd cellht writingline def | ||
664 | /cury curx cury wd cellht writingline def | ||
665 | /cury curx cury wd cellht writingline def | ||
666 | /cury curx cury wd cellht writingline def | ||
667 | /cury curx cury wd cellht writingline def | ||
668 | /cury curx cury wd cellht writingline def | ||
669 | /cury curx cury wd cellht writingline def | ||
670 | /cury curx cury wd cellht writingline def | ||
671 | /cury curx cury wd cellht writingline def | ||
672 | |||
673 | xpos | ||
674 | } def | ||
675 | |||
676 | /record | ||
677 | { | ||
678 | /rtop exch def | ||
679 | /rleft exch def | ||
680 | |||
681 | /xpos rleft def | ||
682 | /ypos rtop def | ||
683 | normalfont | ||
684 | /xpos xpos ypos picid def | ||
685 | /xpos xpos ypos film def | ||
686 | /xpos xpos ypos carrier def | ||
687 | /xpos xpos ypos process def | ||
688 | /xpos xpos ypos geometry def | ||
689 | |||
690 | /ypos ypos 3 cellheight mul sub def | ||
691 | /xpos rleft def | ||
692 | |||
693 | /xpos xpos ypos lens def | ||
694 | /xpos xpos ypos aperture def | ||
695 | /xpos xpos ypos shutter def | ||
696 | |||
697 | /ypos ypos 3 cellheight mul sub def | ||
698 | /xpos rleft def | ||
699 | |||
700 | %/xpos xpos ypos date def | ||
701 | %/ypos ypos 3 cellheight mul sub def | ||
702 | %/xpos rleft def | ||
703 | |||
704 | /xpos xpos ypos notes def | ||
705 | } | ||
706 | def | ||
707 | |||
708 | /xpos planleft def | ||
709 | /ypos plantop def | ||
710 | |||
711 | planleft plantop record | ||
712 | planleft planwidth add plantop record | ||
713 | planleft plantop 5 in sub record | ||
714 | planleft planwidth add plantop 5 in sub record | ||
715 | |||
716 | %/xpos planleft def | ||
717 | %/ypos ypos 3 cellheight mul sub def | ||
718 | %/xpos xpos ypos picid def | ||
719 | %/xpos xpos ypos aperture def | ||
720 | %/xpos xpos ypos shutter def | ||
721 | %/xpos xpos ypos geometry def | ||
722 | |||
723 | %/xpos xpos plantop vor def | ||
724 | %/totalleft xpos def | ||
725 | %/xpos xpos plantop course def | ||
726 | %/xpos xpos plantop altitude def | ||
727 | %/xpos xpos plantop wind def | ||
728 | %/xpos xpos plantop airspeed def | ||
729 | %/xpos xpos plantop tc def | ||
730 | %/xpos xpos plantop th def | ||
731 | %/xpos xpos plantop mh def | ||
732 | %/xpos xpos plantop ch def | ||
733 | %/xpos xpos plantop dist def | ||
734 | %/xpos xpos plantop gs def | ||
735 | %/totalright xpos def | ||
736 | %/xpos xpos plantop time def | ||
737 | %/xpos xpos plantop gph def | ||
738 | %/planright xpos def | ||
739 | %totalleft totalright plantop planheight cellheight sub sub total | ||
740 | |||
741 | %/xpos condleft def | ||
742 | %normalfont | ||
743 | %/xpos xpos condtop frequencies 1 add def | ||
744 | %/xpos xpos condtop atis 1 add def | ||
745 | %/xpos xpos condtop planright condheight layout def | ||
746 | |||
747 | /crop | ||
748 | { | ||
749 | gsave | ||
750 | .2 setlinewidth | ||
751 | .7 .7 .7 setrgbcolor | ||
752 | |||
753 | /bottom plantop 8.5 72 mul sub 36 add def | ||
754 | |||
755 | planleft 4.5 sub plantop 36 add moveto | ||
756 | gsave | ||
757 | 0 -8 rmoveto 0 16 rlineto stroke | ||
758 | grestore | ||
759 | -8 0 rmoveto 16 0 rlineto stroke | ||
760 | |||
761 | planright 4.5 add plantop 36 add moveto | ||
762 | gsave | ||
763 | 0 -8 rmoveto 0 16 rlineto stroke | ||
764 | grestore | ||
765 | -8 0 rmoveto 16 0 rlineto stroke | ||
766 | |||
767 | |||
768 | planleft 4.5 sub bottom moveto | ||
769 | 0 -8 rmoveto 0 16 rlineto stroke | ||
770 | |||
771 | planright 4.5 add bottom moveto | ||
772 | 0 -8 rmoveto 0 16 rlineto stroke | ||
773 | |||
774 | grestore | ||
775 | } def | ||
776 | |||
777 | %crop | ||
778 | |||
779 | showpage | ||
780 | |||
781 | %%EOF \ No newline at end of file | ||
diff --git a/lfrecord.py b/lfrecord.py new file mode 100644 index 0000000..b869033 --- /dev/null +++ b/lfrecord.py | |||
@@ -0,0 +1,863 @@ | |||
1 | # ExiFilm -- Add film exposure metadata to EXIF tags of digital images | ||
2 | # Copyright (C) 2009 James E. Blair <corvus@gnu.org> | ||
3 | # | ||
4 | # This program is free software: you can redistribute it and/or modify | ||
5 | # it under the terms of the GNU General Public License as published by | ||
6 | # the Free Software Foundation, either version 3 of the License, or | ||
7 | # (at your option) any later version. | ||
8 | # | ||
9 | # This program is distributed in the hope that it will be useful, | ||
10 | # but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
11 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
12 | # GNU General Public License for more details. | ||
13 | # | ||
14 | # You should have received a copy of the GNU General Public License | ||
15 | # along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
16 | |||
17 | program = """%%!PS-Adobe-3.0 | ||
18 | %%%%Pages: %(pages)s | ||
19 | %%%%BoundingBox: 0 0 612 792 | ||
20 | %%%%EndComments | ||
21 | |||
22 | %% User servicable: | ||
23 | |||
24 | /in { 72 mul } def | ||
25 | |||
26 | /cellheight 12.75 def | ||
27 | %%/plantop 9.75 in def %% 8.5 - .5 in at top | ||
28 | %%/planleft 7 32 div in def | ||
29 | /plantop 10.25 in def %% 8.5 - .5 in at top | ||
30 | /planleft .75 in def | ||
31 | /planwidth 3 in 15 16 div in add def | ||
32 | |||
33 | %% 3 15/16 in wide | ||
34 | %% 5 in high | ||
35 | |||
36 | /bigfont {/Times-Roman 14 selectfont} def | ||
37 | /normalfont {/Times-Roman 12 selectfont} def | ||
38 | /smallfont {/Times-Roman 10 selectfont} def | ||
39 | |||
40 | /baselineskip 12 def | ||
41 | 1 setlinewidth | ||
42 | |||
43 | %% Less so: | ||
44 | |||
45 | /planheight 21 cellheight mul def | ||
46 | /condtop plantop planheight sub def | ||
47 | /condleft planleft def | ||
48 | /condheight 11 cellheight mul def | ||
49 | |||
50 | /cell {/cury curx cury wd cellht box def} def | ||
51 | /cell1 {curx cury wd1 cellht box pop} def | ||
52 | /cell2cr {/cury curx wd1 add cury wd2 cellht box def} def | ||
53 | /cell3cr {/cury curx wd1 add wd2 add cury wd3 cellht box def} def | ||
54 | /cell2 {curx wd1 add cury wd2 cellht box pop} def | ||
55 | /cell3 {curx wd1 add wd2 add cury wd3 cellht box pop} def | ||
56 | /triangle {newpath curx cury moveto 6 0 cellht 2 div sub rlineto | ||
57 | -6 0 cellht 2 div sub rlineto closepath fill} def | ||
58 | |||
59 | |||
60 | /toppic | ||
61 | { | ||
62 | 0 18 translate | ||
63 | 0.8 -0.8 scale | ||
64 | 0 0 0 setrgbcolor | ||
65 | [] 0 setdash | ||
66 | 1 setlinewidth | ||
67 | 0 setlinejoin | ||
68 | 0 setlinecap | ||
69 | gsave [1 0 0 1 0 0] concat | ||
70 | 0 0 0 setrgbcolor | ||
71 | [] 0 setdash | ||
72 | 0.625 setlinewidth | ||
73 | 1 setlinejoin | ||
74 | 1 setlinecap | ||
75 | newpath | ||
76 | 17.465566 7.6270604 moveto | ||
77 | 17.34201 7.4607341 17.023642 7.1667431 16.801411 7.0511098 curveto | ||
78 | 16.503644 6.896187 16.307292 6.8516095 16.026569 6.7055509 curveto | ||
79 | 15.791517 6.5832505 15.419851 6.5327667 15.14103 6.5327667 curveto | ||
80 | 14.851109 6.5327667 14.510791 6.4751688 14.200137 6.4751688 curveto | ||
81 | 13.906717 6.4751688 13.544314 6.6414571 13.314598 6.8207372 curveto | ||
82 | 13.068846 7.0125432 12.874548 7.2361726 12.595099 7.4542762 curveto | ||
83 | 12.344743 7.6496678 12.125565 7.8753705 11.930944 8.1454035 curveto | ||
84 | 11.751845 8.3938944 11.61173 8.7253772 11.543518 9.0093151 curveto | ||
85 | 11.483134 9.2606497 11.432821 9.6008921 11.432821 9.9308246 curveto | ||
86 | 11.432821 10.284991 11.481859 10.646709 11.543518 10.96752 curveto | ||
87 | 11.606347 11.294419 11.689348 11.459357 11.764903 11.773844 curveto | ||
88 | 11.826229 12.029125 12.085382 12.337715 12.207673 12.464971 curveto | ||
89 | 12.411225 12.676797 12.681981 12.913342 12.927172 13.040921 curveto | ||
90 | 13.208038 13.187056 13.356056 13.321654 13.591326 13.444078 curveto | ||
91 | 13.894704 13.60193 14.210656 13.770986 14.532219 13.904833 curveto | ||
92 | 14.799874 14.016243 15.064115 14.020019 15.362414 14.020019 curveto | ||
93 | 15.668037 14.020019 15.886968 14.041942 16.1926 13.962421 curveto | ||
94 | 16.488636 13.885412 16.686938 13.733028 16.912108 13.674451 curveto | ||
95 | 17.175607 13.605906 17.382184 13.372271 17.576263 13.271294 curveto | ||
96 | 17.802565 13.15354 17.966257 13.038239 18.12972 12.868137 curveto | ||
97 | 18.33059 12.659107 18.448373 12.636072 18.517146 12.349785 curveto | ||
98 | 18.58201 12.07978 18.683187 12.005006 18.683187 11.658657 curveto | ||
99 | 18.683187 11.370687 18.683187 11.082707 18.683187 10.794746 curveto | ||
100 | 18.683187 10.482732 18.689036 10.243133 18.627843 9.9884225 curveto | ||
101 | 18.56315 9.7191599 18.57249 9.4050915 18.57249 9.1245109 curveto | ||
102 | 18.57249 8.8389752 18.46301 8.6086787 18.351105 8.3757857 curveto | ||
103 | 18.246685 8.158462 18.001799 8.0698776 17.852991 7.9150309 curveto | ||
104 | 17.675889 7.730729 17.748724 7.7007222 17.465566 7.6270604 curveto | ||
105 | closepath | ||
106 | stroke | ||
107 | 0 0 0 setrgbcolor | ||
108 | [] 0 setdash | ||
109 | 0.625 setlinewidth | ||
110 | 1 setlinejoin | ||
111 | 1 setlinecap | ||
112 | newpath | ||
113 | 18.908969 9.1187484 moveto | ||
114 | 19.132586 9.2148318 19.670178 9.5204546 19.889559 9.6723899 curveto | ||
115 | 20.225854 9.9053021 20.525329 9.9224118 20.835946 10.076851 curveto | ||
116 | 21.210027 10.262847 21.490107 10.364636 21.849811 10.465301 curveto | ||
117 | 22.38606 10.615383 21.920523 10.684453 21.563764 10.76915 curveto | ||
118 | 21.276372 10.837386 20.927903 10.920113 20.619207 10.993399 curveto | ||
119 | 20.270784 11.076118 19.970536 11.147404 19.607192 11.233666 curveto | ||
120 | 19.449759 11.271042 19.292336 11.308417 19.134913 11.345791 curveto | ||
121 | stroke | ||
122 | 0 0 0 setrgbcolor | ||
123 | [] 0 setdash | ||
124 | 0.625 setlinewidth | ||
125 | 1 setlinejoin | ||
126 | 1 setlinecap | ||
127 | newpath | ||
128 | 12.479003 7.3178906 moveto | ||
129 | 12.297483 7.2051594 10.437915 6.743884 10.199405 6.6961819 curveto | ||
130 | 9.9461844 6.6455378 8.2389814 6.412102 8.4897064 6.4371367 curveto | ||
131 | 8.9210134 6.4802021 7.6023054 6.3853275 7.3499064 6.3853275 curveto | ||
132 | 7.1865764 6.3853275 6.6748094 6.3424179 6.2101074 6.3853275 curveto | ||
133 | 5.9802984 6.4065477 4.6730454 6.5580544 4.3967904 6.6961819 curveto | ||
134 | 4.1597714 6.8146914 3.9322444 6.8766459 3.6714644 7.0070363 curveto | ||
135 | 3.3812444 7.1521462 3.1878204 7.2920552 2.9461374 7.4733178 curveto | ||
136 | 2.7386724 7.6289163 2.4671594 7.8455027 2.2726194 7.9914084 curveto | ||
137 | 2.0299164 8.1734353 1.8916084 8.3206101 1.7027194 8.5094989 curveto | ||
138 | 1.5052674 8.706951 1.4151344 8.8256235 1.2882464 9.0793985 curveto | ||
139 | 1.1595274 9.3368386 1.0339524 9.4843697 0.92558337 9.7011073 curveto | ||
140 | 0.78229837 9.9876779 0.64040737 10.116486 0.56292037 10.426434 curveto | ||
141 | 0.50396737 10.662246 0.51591437 10.873501 0.45930237 11.099952 curveto | ||
142 | 0.39136637 11.371693 0.56233537 11.565062 0.66653837 11.77347 curveto | ||
143 | 0.76972037 11.979834 1.0569594 12.231766 1.1846294 12.395178 curveto | ||
144 | 1.4171204 12.692756 1.6462124 12.974507 1.9099554 13.172314 curveto | ||
145 | 2.2042814 13.393059 2.9527384 13.952751 3.2569914 14.104877 curveto | ||
146 | 4.1361764 14.565305 4.7738594 14.88324 5.7438264 14.985631 curveto | ||
147 | 6.1202154 15.079729 7.3525084 15.363749 8.8005604 15.192867 curveto | ||
148 | 9.8815834 15.065298 10.824802 14.750645 11.494631 14.260304 curveto | ||
149 | 12.29744 13.766723 12.403624 13.534597 12.789858 13.120505 curveto | ||
150 | stroke | ||
151 | grestore | ||
152 | } def | ||
153 | |||
154 | /sidepic | ||
155 | { | ||
156 | 0 18 translate | ||
157 | 0.8 -0.8 scale | ||
158 | 0 0 0 setrgbcolor | ||
159 | [] 0 setdash | ||
160 | 1 setlinewidth | ||
161 | 0 setlinejoin | ||
162 | 0 setlinecap | ||
163 | gsave [1 0 0 1 0 0] concat | ||
164 | 0 0 0 setrgbcolor | ||
165 | [] 0 setdash | ||
166 | 0.625 setlinewidth | ||
167 | 1 setlinejoin | ||
168 | 1 setlinecap | ||
169 | newpath | ||
170 | 17.41745 3.3235764 moveto | ||
171 | 17.28754 3.1486964 16.9528 2.8395864 16.71914 2.7180064 curveto | ||
172 | 16.40606 2.5551164 16.19961 2.5082464 15.90445 2.3546764 curveto | ||
173 | 15.65731 2.2260864 15.26653 2.1730064 14.97337 2.1730064 curveto | ||
174 | 14.66854 2.1730064 14.31072 2.1124464 13.98409 2.1124464 curveto | ||
175 | 13.67558 2.1124464 13.29454 2.2872864 13.05301 2.4757864 curveto | ||
176 | 12.79462 2.6774564 12.59033 2.9125864 12.296511 3.1419064 curveto | ||
177 | 12.033281 3.3473464 11.802831 3.5846564 11.598201 3.8685764 curveto | ||
178 | 11.409891 4.1298464 11.262571 4.4783764 11.190851 4.7769164 curveto | ||
179 | 11.127361 5.0411764 11.074461 5.3989164 11.074461 5.7458164 curveto | ||
180 | 11.074461 6.1181964 11.126021 6.4985164 11.190851 6.8358264 curveto | ||
181 | 11.256911 7.1795364 11.344181 7.3529564 11.423621 7.6836164 curveto | ||
182 | 11.488101 7.9520264 11.760581 8.2764864 11.889161 8.4102864 curveto | ||
183 | 12.103181 8.6330064 12.387861 8.8817164 12.64566 9.0158564 curveto | ||
184 | 12.94097 9.1695064 13.0966 9.3110264 13.34397 9.4397464 curveto | ||
185 | 13.66295 9.6057164 13.99515 9.7834664 14.33325 9.9241964 curveto | ||
186 | 14.61467 10.041336 14.8925 10.045306 15.20614 10.045306 curveto | ||
187 | 15.52748 10.045306 15.75767 10.068356 16.07902 9.9847464 curveto | ||
188 | 16.39028 9.9037764 16.59878 9.7435564 16.83553 9.6819664 curveto | ||
189 | 17.11258 9.6098964 17.32978 9.3642464 17.53384 9.2580764 curveto | ||
190 | 17.77178 9.1342664 17.94389 9.0130364 18.11576 8.8341864 curveto | ||
191 | 18.32696 8.6144064 18.4508 8.5901864 18.52311 8.2891764 curveto | ||
192 | 18.59131 8.0052864 18.69769 7.9266664 18.69769 7.5625064 curveto | ||
193 | 18.69769 7.2597264 18.69769 6.9569364 18.69769 6.6541664 curveto | ||
194 | 18.69769 6.3261064 18.70384 6.0741864 18.6395 5.8063764 curveto | ||
195 | 18.57148 5.5232664 18.5813 5.1930464 18.5813 4.8980364 curveto | ||
196 | 18.5813 4.5978164 18.46619 4.3556764 18.34853 4.1108064 curveto | ||
197 | 18.23874 3.8823064 17.98126 3.7891664 17.8248 3.6263564 curveto | ||
198 | 17.63859 3.4325764 17.71517 3.4010264 17.41745 3.3235764 curveto | ||
199 | closepath | ||
200 | stroke | ||
201 | 0 0 0 setrgbcolor | ||
202 | [] 0 setdash | ||
203 | 0.625 setlinewidth | ||
204 | 1 setlinejoin | ||
205 | 1 setlinecap | ||
206 | newpath | ||
207 | 18.94656 5.9379964 moveto | ||
208 | 19.1584 6.0815564 19.65288 6.5037464 19.84927 6.7041364 curveto | ||
209 | 20.15032 7.0113264 20.45615 7.0883864 20.74625 7.3094564 curveto | ||
210 | 21.09562 7.5756964 21.36463 7.7363464 21.716081 7.9116264 curveto | ||
211 | 22.240021 8.1729464 21.745631 8.1519364 21.36046 8.1686364 curveto | ||
212 | 21.05018 8.1820964 20.67396 8.1984064 20.34068 8.2128564 curveto | ||
213 | 19.96451 8.2291664 19.64035 8.2432264 19.24807 8.2602364 curveto | ||
214 | 19.0781 8.2676064 18.90814 8.2749764 18.73818 8.2823464 curveto | ||
215 | stroke | ||
216 | 0 0 0 setrgbcolor | ||
217 | [] 0 setdash | ||
218 | 0.625 setlinewidth | ||
219 | 1 setlinejoin | ||
220 | 1 setlinecap | ||
221 | newpath | ||
222 | 11.058081 6.3609964 moveto | ||
223 | 10.898991 6.3609964 10.297991 6.3609964 9.9236506 6.3609964 curveto | ||
224 | 9.6528706 6.3609964 9.2296906 6.4606964 9.0019306 6.5275864 curveto | ||
225 | 8.6792106 6.6223764 8.3901106 6.6031664 8.0802106 6.6941864 curveto | ||
226 | 7.7549906 6.7896964 7.3425006 6.8692064 7.0875806 6.9440764 curveto | ||
227 | 6.7203606 7.0519264 6.3784006 7.1731864 6.0240506 7.2772664 curveto | ||
228 | 5.6876206 7.3760764 5.4495006 7.5314764 5.1732306 7.6937564 curveto | ||
229 | 4.8089906 7.9077164 4.5570206 8.1390264 4.1806106 8.3601364 curveto | ||
230 | 3.8315206 8.5651864 3.5054206 9.0700664 3.2588806 9.3597064 curveto | ||
231 | 2.9162706 9.7622164 2.6772606 10.143226 2.4789706 10.609166 curveto | ||
232 | 2.2757806 11.086586 2.1067606 11.567026 1.9117506 12.025216 curveto | ||
233 | 1.7229306 12.468886 1.5183906 12.957456 1.4154406 13.441276 curveto | ||
234 | 1.3145406 13.915446 1.0273606 14.353136 0.84822058 14.774036 curveto | ||
235 | 0.65579058 15.226186 0.63552058 15.643266 0.63552058 15.773606 curveto | ||
236 | stroke | ||
237 | 0 0 0 setrgbcolor | ||
238 | [] 0 setdash | ||
239 | 0.625 setlinewidth | ||
240 | 1 setlinejoin | ||
241 | 1 setlinecap | ||
242 | newpath | ||
243 | 14.33933 10.302876 moveto | ||
244 | 14.20693 10.595156 14.14423 11.072806 13.90194 11.429396 curveto | ||
245 | 13.70442 11.720106 13.37015 12.016406 13.17297 12.234056 curveto | ||
246 | 12.88897 12.547546 12.59356 12.873636 12.298201 13.199656 curveto | ||
247 | 12.020021 13.506716 11.823431 13.804186 11.496341 14.165246 curveto | ||
248 | 11.169801 14.525686 10.912571 14.749106 10.548671 15.050376 curveto | ||
249 | 10.232431 15.312176 9.7936806 15.426826 9.4552106 15.613636 curveto | ||
250 | 9.1243106 15.796266 8.5739906 15.756236 8.2159606 15.855036 curveto | ||
251 | 7.8258106 15.962696 7.3481706 15.832996 6.9767106 15.935496 curveto | ||
252 | 6.5954506 16.040716 6.0587306 15.935496 5.6645506 15.935496 curveto | ||
253 | 5.2171706 15.935496 4.8659706 16.015966 4.4253006 16.015966 curveto | ||
254 | 4.0136906 16.015966 3.5635006 15.935496 3.1131506 15.935496 curveto | ||
255 | 2.7207406 15.935496 2.2370206 15.733586 2.0196906 15.613636 curveto | ||
256 | 1.7663706 15.473826 1.1338906 15.325916 1.0720306 15.291776 curveto | ||
257 | stroke | ||
258 | 0 0 0 setrgbcolor | ||
259 | [] 0 setdash | ||
260 | 0.63630593 setlinewidth | ||
261 | 1 setlinejoin | ||
262 | 1 setlinecap | ||
263 | newpath | ||
264 | 9.9264619 15.524615 moveto | ||
265 | 9.601864 15.336485 9.9988871 16.363201 9.9988871 16.783897 curveto | ||
266 | 9.9988871 17.343824 9.8991612 17.884929 9.9988871 18.462927 curveto | ||
267 | 10.104136 19.072974 9.9702746 19.353219 10.288574 19.722199 curveto | ||
268 | 10.538501 20.011916 10.948726 20.272725 11.157634 20.393812 curveto | ||
269 | 11.29979 20.476203 11.505777 20.474522 11.519735 20.477757 curveto | ||
270 | stroke | ||
271 | 0 0 0 setrgbcolor | ||
272 | [] 0 setdash | ||
273 | 0.625 setlinewidth | ||
274 | 1 setlinejoin | ||
275 | 1 setlinecap | ||
276 | newpath | ||
277 | 10.213238 19.68757 moveto | ||
278 | 10.382008 19.78072 9.6081369 20.54456 9.4113669 20.65317 curveto | ||
279 | 9.2846369 20.72311 9.1736069 20.82462 9.0468769 20.89457 curveto | ||
280 | stroke | ||
281 | 0 0 0 setrgbcolor | ||
282 | [] 0 setdash | ||
283 | 0.625 setlinewidth | ||
284 | 1 setlinejoin | ||
285 | 1 setlinecap | ||
286 | newpath | ||
287 | 6.5393206 16.015966 moveto | ||
288 | 6.2133206 16.195896 6.5393206 16.820626 6.5393206 17.222956 curveto | ||
289 | 6.5393206 17.627916 6.5393206 17.996046 6.5393206 18.429956 curveto | ||
290 | 6.5393206 18.885926 6.5393206 19.341896 6.5393206 19.797876 curveto | ||
291 | 6.5393206 19.821846 7.2722806 20.242636 7.3411906 20.280676 curveto | ||
292 | 7.3483106 20.418036 7.4383906 20.334316 7.4869906 20.361136 curveto | ||
293 | stroke | ||
294 | 0 0 0 setrgbcolor | ||
295 | [] 0 setdash | ||
296 | 0.625 setlinewidth | ||
297 | 1 setlinejoin | ||
298 | 1 setlinecap | ||
299 | newpath | ||
300 | 6.5393206 19.797876 moveto | ||
301 | 6.8774206 19.984476 6.0047406 20.387956 5.7374506 20.683006 curveto | ||
302 | 5.6645606 20.763466 5.5916606 20.843936 5.5187606 20.924396 curveto | ||
303 | stroke | ||
304 | gsave | ||
305 | 0 0 0 setrgbcolor | ||
306 | newpath | ||
307 | 16.59914 4.9921064 moveto | ||
308 | 16.75393 5.5208564 16.53852 5.6023764 16.16176 5.3944364 curveto | ||
309 | 15.78595 5.1870264 16.27681 4.8497864 16.59914 4.9921064 curveto | ||
310 | closepath | ||
311 | fill | ||
312 | grestore | ||
313 | 0 0 0 setrgbcolor | ||
314 | [] 0 setdash | ||
315 | 0.625 setlinewidth | ||
316 | 1 setlinejoin | ||
317 | 1 setlinecap | ||
318 | newpath | ||
319 | 16.59914 4.9921064 moveto | ||
320 | 16.75393 5.5208564 16.53852 5.6023764 16.16176 5.3944364 curveto | ||
321 | 15.78595 5.1870264 16.27681 4.8497864 16.59914 4.9921064 curveto | ||
322 | closepath | ||
323 | stroke | ||
324 | grestore | ||
325 | } def | ||
326 | |||
327 | /cameraview | ||
328 | { | ||
329 | /crtilt exch def %%or swing | ||
330 | /crrise exch def %%or shift | ||
331 | |||
332 | /cftilt exch def %%or swing | ||
333 | /cfrise exch def %%or shift | ||
334 | |||
335 | 30 10 translate | ||
336 | -4 0 moveto 28 0 rlineto stroke | ||
337 | |||
338 | /ftopx -2.5 cftilt mul def | ||
339 | /ftopy 5 cfrise mul 5 add def | ||
340 | /fbotx 2.5 cftilt mul def | ||
341 | /fboty 5 cfrise mul -5 add def | ||
342 | |||
343 | /rtopx 20 -2.5 crtilt mul add def | ||
344 | /rtopy 5 crrise mul 5 add def | ||
345 | /rbotx 20 2.5 crtilt mul add def | ||
346 | /rboty 5 crrise mul -5 add def | ||
347 | |||
348 | ftopx ftopy moveto | ||
349 | fbotx fboty lineto | ||
350 | rbotx rboty lineto | ||
351 | rtopx rtopy lineto | ||
352 | ftopx ftopy lineto | ||
353 | stroke | ||
354 | |||
355 | } def | ||
356 | |||
357 | /greybox | ||
358 | { | ||
359 | /height exch def | ||
360 | /width exch def | ||
361 | /top exch def | ||
362 | /left exch def | ||
363 | |||
364 | /bottom top height sub def | ||
365 | |||
366 | .8 .8 .8 setrgbcolor | ||
367 | left bottom width height rectfill | ||
368 | 0 0 0 setrgbcolor | ||
369 | left bottom width height rectstroke | ||
370 | bottom | ||
371 | } def | ||
372 | |||
373 | /blackbox | ||
374 | { | ||
375 | /height exch def | ||
376 | /width exch def | ||
377 | /top exch def | ||
378 | /left exch def | ||
379 | |||
380 | /bottom top height sub def | ||
381 | |||
382 | 0 0 0 setrgbcolor | ||
383 | left bottom width height rectfill | ||
384 | left bottom width height rectstroke | ||
385 | bottom | ||
386 | } def | ||
387 | |||
388 | /box | ||
389 | { | ||
390 | /height exch def | ||
391 | /width exch def | ||
392 | /top exch def | ||
393 | /left exch def | ||
394 | |||
395 | /bottom top height sub def | ||
396 | |||
397 | 0 0 0 setrgbcolor | ||
398 | left bottom width height rectstroke | ||
399 | bottom | ||
400 | } def | ||
401 | |||
402 | /writingline | ||
403 | { | ||
404 | /height exch def | ||
405 | /width exch def | ||
406 | /top exch def | ||
407 | /left exch def | ||
408 | |||
409 | /bottom top height sub def | ||
410 | |||
411 | .125 setlinewidth | ||
412 | left bottom moveto width 0 rlineto stroke | ||
413 | 1 setlinewidth | ||
414 | bottom | ||
415 | } def | ||
416 | |||
417 | |||
418 | /centertext | ||
419 | { | ||
420 | /s exch def | ||
421 | /x2 exch def | ||
422 | /x1 exch def | ||
423 | /y exch def | ||
424 | |||
425 | x2 x1 sub 2 div x1 add %% midpoint | ||
426 | s stringwidth pop 2 div %% half the string width | ||
427 | sub %% move left to start | ||
428 | |||
429 | y baselineskip sub moveto s show | ||
430 | y baselineskip sub | ||
431 | } def | ||
432 | |||
433 | /righttext | ||
434 | { | ||
435 | /s exch def | ||
436 | /x2 exch def | ||
437 | /x1 exch def | ||
438 | /y exch def | ||
439 | |||
440 | x2 | ||
441 | s stringwidth pop | ||
442 | sub 1 sub | ||
443 | |||
444 | y baselineskip sub moveto s show | ||
445 | y baselineskip sub | ||
446 | } def | ||
447 | |||
448 | /lefttext | ||
449 | { | ||
450 | /s exch def | ||
451 | /x2 exch def | ||
452 | /x1 exch def | ||
453 | /y exch def | ||
454 | |||
455 | x1 1 add | ||
456 | |||
457 | y baselineskip sub moveto s show | ||
458 | y baselineskip sub | ||
459 | } def | ||
460 | |||
461 | |||
462 | /picid | ||
463 | { | ||
464 | /cury exch def | ||
465 | /curx exch def | ||
466 | /wd 42 def | ||
467 | /headht 1 cellheight mul def | ||
468 | /cellht 2 cellheight mul def | ||
469 | |||
470 | curx cury wd headht greybox | ||
471 | |||
472 | cury 2 add | ||
473 | curx curx wd add (ID) centertext | ||
474 | pop | ||
475 | |||
476 | /cury exch def %% add height change from box | ||
477 | |||
478 | cell | ||
479 | |||
480 | bigfont | ||
481 | cury 20 add curx curx wd add idtext centertext pop | ||
482 | smallfont | ||
483 | |||
484 | xpos wd add | ||
485 | } def | ||
486 | |||
487 | /aperture | ||
488 | { | ||
489 | /cury exch def | ||
490 | /curx exch def | ||
491 | /wd 68 def | ||
492 | /headht 1 cellheight mul def | ||
493 | /cellht 2 cellheight mul def | ||
494 | |||
495 | curx cury wd headht greybox | ||
496 | |||
497 | cury 2 add | ||
498 | curx curx wd add (Aperture (f/x)) centertext | ||
499 | pop | ||
500 | |||
501 | /cury exch def %% add height change from box | ||
502 | |||
503 | cell | ||
504 | |||
505 | bigfont | ||
506 | cury 20 add curx curx wd add aperturetext centertext pop | ||
507 | smallfont | ||
508 | |||
509 | xpos wd add | ||
510 | } def | ||
511 | |||
512 | /shutter | ||
513 | { | ||
514 | /cury exch def | ||
515 | /curx exch def | ||
516 | /wd 68 def | ||
517 | /headht 1 cellheight mul def | ||
518 | /cellht 2 cellheight mul def | ||
519 | |||
520 | curx cury wd headht greybox | ||
521 | |||
522 | cury 2 add | ||
523 | curx curx wd add (Shutter (sec)) centertext | ||
524 | pop | ||
525 | |||
526 | /cury exch def %% add height change from box | ||
527 | |||
528 | cell | ||
529 | |||
530 | bigfont | ||
531 | cury 20 add curx curx wd add shuttertext centertext pop | ||
532 | smallfont | ||
533 | |||
534 | xpos wd add | ||
535 | } def | ||
536 | |||
537 | /geometry | ||
538 | { | ||
539 | /rrise exch def | ||
540 | /rtilt exch def | ||
541 | /rswing exch def | ||
542 | /rshift exch def | ||
543 | |||
544 | /frise exch def | ||
545 | /ftilt exch def | ||
546 | /fswing exch def | ||
547 | /fshift exch def | ||
548 | |||
549 | /cury exch def | ||
550 | /curx exch def | ||
551 | /wd 74 def | ||
552 | /headht 1 cellheight mul def | ||
553 | /cellht 2.5 cellheight mul def | ||
554 | |||
555 | curx cury wd headht greybox | ||
556 | |||
557 | cury 2 add | ||
558 | curx curx wd add (Geometry) centertext | ||
559 | pop | ||
560 | |||
561 | /cury exch def %% add height change from box | ||
562 | |||
563 | cell | ||
564 | |||
565 | gsave | ||
566 | curx 3 add cury 6 add translate toppic | ||
567 | grestore | ||
568 | gsave | ||
569 | curx 3 add cury 6 add translate | ||
570 | fshift fswing rshift rswing cameraview | ||
571 | grestore | ||
572 | |||
573 | cell | ||
574 | |||
575 | gsave | ||
576 | curx 3 add cury 6 add translate sidepic | ||
577 | grestore | ||
578 | gsave | ||
579 | curx 3 add cury 6 add translate | ||
580 | frise ftilt rrise rtilt cameraview | ||
581 | grestore | ||
582 | |||
583 | xpos wd add | ||
584 | } def | ||
585 | |||
586 | /film | ||
587 | { | ||
588 | /cury exch def | ||
589 | /curx exch def | ||
590 | /wd 52 def | ||
591 | /headht 1 cellheight mul def | ||
592 | /cellht 2 cellheight mul def | ||
593 | |||
594 | curx cury wd headht greybox | ||
595 | |||
596 | cury 2 add | ||
597 | curx curx wd add (Film) centertext | ||
598 | pop | ||
599 | |||
600 | /cury exch def %% add height change from box | ||
601 | |||
602 | cell | ||
603 | |||
604 | bigfont | ||
605 | cury 20 add curx curx wd add filmtext centertext pop | ||
606 | smallfont | ||
607 | |||
608 | xpos wd add | ||
609 | } def | ||
610 | |||
611 | /carrier | ||
612 | { | ||
613 | /cury exch def | ||
614 | /curx exch def | ||
615 | /wd 42 def | ||
616 | /headht 1 cellheight mul def | ||
617 | /cellht 2 cellheight mul def | ||
618 | |||
619 | curx cury wd headht greybox | ||
620 | |||
621 | cury 2 add | ||
622 | curx curx wd add (Carrier) centertext | ||
623 | pop | ||
624 | |||
625 | /cury exch def %% add height change from box | ||
626 | |||
627 | cell | ||
628 | |||
629 | bigfont | ||
630 | cury 20 add curx curx wd add carriertext centertext pop | ||
631 | smallfont | ||
632 | |||
633 | xpos wd add | ||
634 | } def | ||
635 | |||
636 | /lens | ||
637 | { | ||
638 | /cury exch def | ||
639 | /curx exch def | ||
640 | /wd 42 def | ||
641 | /headht 1 cellheight mul def | ||
642 | /cellht 2 cellheight mul def | ||
643 | |||
644 | curx cury wd headht greybox | ||
645 | |||
646 | cury 2 add | ||
647 | curx curx wd add (Lens) centertext | ||
648 | pop | ||
649 | |||
650 | /cury exch def %% add height change from box | ||
651 | |||
652 | cell | ||
653 | |||
654 | bigfont | ||
655 | cury 20 add curx curx wd add lenstext centertext pop | ||
656 | smallfont | ||
657 | |||
658 | xpos wd add | ||
659 | } def | ||
660 | |||
661 | /process | ||
662 | { | ||
663 | /cury exch def | ||
664 | /curx exch def | ||
665 | /wd 42 def | ||
666 | /headht 1 cellheight mul def | ||
667 | /cellht 2 cellheight mul def | ||
668 | |||
669 | curx cury wd headht greybox | ||
670 | |||
671 | cury 2 add | ||
672 | curx curx wd add (Process) centertext | ||
673 | pop | ||
674 | |||
675 | /cury exch def %% add height change from box | ||
676 | |||
677 | cell | ||
678 | |||
679 | bigfont | ||
680 | cury 20 add curx curx wd add processtext centertext pop | ||
681 | smallfont | ||
682 | |||
683 | xpos wd add | ||
684 | } def | ||
685 | |||
686 | /date | ||
687 | { | ||
688 | /cury exch def | ||
689 | /curx exch def | ||
690 | |||
691 | /wd 252 108 sub def | ||
692 | /cellht 1.5 cellheight mul def | ||
693 | |||
694 | curx cury wd 2 cellht mul box pop | ||
695 | |||
696 | /cury curx cury wd cellht writingline def | ||
697 | /cury curx cury wd cellht writingline def | ||
698 | |||
699 | /cury cury 2 cellht mul add def | ||
700 | /curx curx wd add def | ||
701 | |||
702 | /wd 108 def | ||
703 | /headht 1 cellheight mul def | ||
704 | /cellht 2 cellheight mul def | ||
705 | |||
706 | curx cury wd headht greybox | ||
707 | |||
708 | cury 2 add | ||
709 | curx curx wd add (Date) centertext | ||
710 | pop | ||
711 | |||
712 | /cury exch def %% add height change from box | ||
713 | |||
714 | cell | ||
715 | |||
716 | %% draw the writing lines | ||
717 | |||
718 | xpos | ||
719 | } def | ||
720 | |||
721 | /notes | ||
722 | { | ||
723 | /cury exch def | ||
724 | /curx exch def | ||
725 | |||
726 | /wd 252 def | ||
727 | %%/headht 1 cellheight mul def | ||
728 | /cellht 1.5 cellheight mul def | ||
729 | /boxht 4.5 in 6 cellheight mul sub def %% 5in - header so far | ||
730 | |||
731 | %%curx cury wd headht greybox | ||
732 | |||
733 | %%cury 2 add | ||
734 | %%curx curx wd add (Process) centertext | ||
735 | %%pop | ||
736 | |||
737 | %%/cury exch def %% add height change from box | ||
738 | |||
739 | curx cury wd boxht box pop | ||
740 | |||
741 | %%/cury curx 10 add cury wd 20 sub cellht writingline def | ||
742 | |||
743 | curx cury %% save for returning to print text | ||
744 | /cury curx cury wd cellht writingline def | ||
745 | /cury curx cury wd cellht writingline def | ||
746 | /cury curx cury wd cellht writingline def | ||
747 | /cury curx cury wd cellht writingline def | ||
748 | /cury curx cury wd cellht writingline def | ||
749 | /cury curx cury wd cellht writingline def | ||
750 | /cury curx cury wd cellht writingline def | ||
751 | /cury curx cury wd cellht writingline def | ||
752 | /cury curx cury wd cellht writingline def | ||
753 | /cury curx cury wd cellht writingline def | ||
754 | /cury curx cury wd cellht writingline def | ||
755 | /cury curx cury wd cellht writingline def | ||
756 | |||
757 | moveto %% saved starting point | ||
758 | normalfont | ||
759 | notelines | ||
760 | { | ||
761 | 0 0 cellht sub rmoveto | ||
762 | currentpoint | ||
763 | 2 2 rmoveto | ||
764 | 3 -1 roll show | ||
765 | moveto | ||
766 | } forall | ||
767 | smallfont | ||
768 | |||
769 | xpos | ||
770 | } def | ||
771 | |||
772 | /record | ||
773 | { | ||
774 | /notelines exch def | ||
775 | |||
776 | /rrise exch def | ||
777 | /rtilt exch def | ||
778 | /rswing exch def | ||
779 | /rshift exch def | ||
780 | |||
781 | /frise exch def | ||
782 | /ftilt exch def | ||
783 | /fswing exch def | ||
784 | /fshift exch def | ||
785 | |||
786 | /shuttertext exch def | ||
787 | /aperturetext exch def | ||
788 | /lenstext exch def | ||
789 | |||
790 | /processtext exch def | ||
791 | /carriertext exch def | ||
792 | /filmtext exch def | ||
793 | /idtext exch def | ||
794 | |||
795 | /rtop exch def | ||
796 | /rleft exch def | ||
797 | |||
798 | /xpos rleft def | ||
799 | /ypos rtop def | ||
800 | smallfont | ||
801 | /xpos xpos ypos picid def | ||
802 | /xpos xpos ypos film def | ||
803 | /xpos xpos ypos carrier def | ||
804 | /xpos xpos ypos process def | ||
805 | /xpos xpos ypos | ||
806 | frise ftilt fswing fshift | ||
807 | rrise rtilt rswing rshift | ||
808 | geometry def | ||
809 | |||
810 | /ypos ypos 3 cellheight mul sub def | ||
811 | /xpos rleft def | ||
812 | |||
813 | /xpos xpos ypos lens def | ||
814 | /xpos xpos ypos aperture def | ||
815 | /xpos xpos ypos shutter def | ||
816 | |||
817 | /ypos ypos 3 cellheight mul sub def | ||
818 | /xpos rleft def | ||
819 | |||
820 | %%/xpos xpos ypos date def | ||
821 | %%/ypos ypos 3 cellheight mul sub def | ||
822 | %%/xpos rleft def | ||
823 | |||
824 | /xpos xpos ypos notes def | ||
825 | } | ||
826 | def | ||
827 | |||
828 | %(code)s | ||
829 | |||
830 | /crop | ||
831 | { | ||
832 | gsave | ||
833 | .2 setlinewidth | ||
834 | .7 .7 .7 setrgbcolor | ||
835 | |||
836 | /bottom plantop 8.5 72 mul sub 36 add def | ||
837 | |||
838 | planleft 4.5 sub plantop 36 add moveto | ||
839 | gsave | ||
840 | 0 -8 rmoveto 0 16 rlineto stroke | ||
841 | grestore | ||
842 | -8 0 rmoveto 16 0 rlineto stroke | ||
843 | |||
844 | planright 4.5 add plantop 36 add moveto | ||
845 | gsave | ||
846 | 0 -8 rmoveto 0 16 rlineto stroke | ||
847 | grestore | ||
848 | -8 0 rmoveto 16 0 rlineto stroke | ||
849 | |||
850 | |||
851 | planleft 4.5 sub bottom moveto | ||
852 | 0 -8 rmoveto 0 16 rlineto stroke | ||
853 | |||
854 | planright 4.5 add bottom moveto | ||
855 | 0 -8 rmoveto 0 16 rlineto stroke | ||
856 | |||
857 | grestore | ||
858 | } def | ||
859 | |||
860 | %%crop | ||
861 | |||
862 | %%%%EOF | ||
863 | """ | ||
diff --git a/printrecord.py b/printrecord.py new file mode 100644 index 0000000..65dc48a --- /dev/null +++ b/printrecord.py | |||
@@ -0,0 +1,187 @@ | |||
1 | #!/usr/bin/python | ||
2 | |||
3 | # ExiFilm -- Add film exposure metadata to EXIF tags of digital images | ||
4 | # Copyright (C) 2009 James E. Blair <corvus@gnu.org> | ||
5 | # | ||
6 | # This program is free software: you can redistribute it and/or modify | ||
7 | # it under the terms of the GNU General Public License as published by | ||
8 | # the Free Software Foundation, either version 3 of the License, or | ||
9 | # (at your option) any later version. | ||
10 | # | ||
11 | # This program is distributed in the hope that it will be useful, | ||
12 | # but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | # GNU General Public License for more details. | ||
15 | # | ||
16 | # You should have received a copy of the GNU General Public License | ||
17 | # along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
18 | |||
19 | import os, sys | ||
20 | import pyexiv2 | ||
21 | import datetime | ||
22 | import decimal, fractions | ||
23 | import re | ||
24 | |||
25 | from exifilm import * | ||
26 | import lfrecord | ||
27 | |||
28 | class MyImage(object): | ||
29 | def __init__(self, fn): | ||
30 | if fn: | ||
31 | image = pyexiv2.Image(fn) | ||
32 | image.readMetadata() | ||
33 | keys = image.exifKeys() | ||
34 | self.image = image | ||
35 | else: | ||
36 | keys = [] | ||
37 | |||
38 | def get(key, default=''): | ||
39 | if key in keys: | ||
40 | return image[key] | ||
41 | return default | ||
42 | |||
43 | self.date = get('Exif.Photo.DateTimeOriginal', '') | ||
44 | |||
45 | self.shutter=from_rational(get('Exif.Photo.ExposureTime')) | ||
46 | self.aperture=to_fstop(from_rational(get('Exif.Photo.FNumber'))) | ||
47 | self.lens=from_rational(get('Exif.Photo.FocalLength')) | ||
48 | |||
49 | self.description=get('Exif.Image.ImageDescription') | ||
50 | extras, comments = decode_comments(get('Exif.Photo.UserComment')) | ||
51 | self.comments=comments | ||
52 | |||
53 | self.id = extras.get(ID, '') | ||
54 | self.film = extras.get(FILM, '') | ||
55 | self.carrier = extras.get(CARRIER, '') | ||
56 | self.process = extras.get(PROCESS, '') | ||
57 | |||
58 | self.front_movements = extras.get(FRONT_MOVEMENTS, '').split('/') | ||
59 | self.rear_movements = extras.get(REAR_MOVEMENTS, '').split('/') | ||
60 | |||
61 | def render(self): | ||
62 | r = ' (%s) (%s) (%s) (%s)\n' % (self.id, self.film, self.carrier, self.process) | ||
63 | r += ' (%s) (%s) (%s)\n' % (self.lens, self.aperture, self.shutter) | ||
64 | r += ' ' | ||
65 | |||
66 | if 'rising' in self.front_movements: r += '1 ' | ||
67 | elif 'falling' in self.front_movements: r += '-1 ' | ||
68 | else: r += '0 ' | ||
69 | |||
70 | if 'forward tilt' in self.front_movements: r += '1 ' | ||
71 | elif 'backward tilt' in self.front_movements: r += '-1 ' | ||
72 | else: r += '0 ' | ||
73 | |||
74 | if 'left swing' in self.front_movements: r += '1 ' | ||
75 | elif 'right swing' in self.front_movements: r += '-1 ' | ||
76 | else: r += '0 ' | ||
77 | |||
78 | if 'left shift' in self.front_movements: r += '1 ' | ||
79 | elif 'right shift' in self.front_movements: r += '-1 ' | ||
80 | else: r += '0 ' | ||
81 | |||
82 | r += ' ' | ||
83 | |||
84 | if 'rising' in self.rear_movements: r += '1 ' | ||
85 | elif 'falling' in self.rear_movements: r += '-1 ' | ||
86 | else: r += '0 ' | ||
87 | |||
88 | if 'forward tilt' in self.rear_movements: r += '1 ' | ||
89 | elif 'backward tilt' in self.rear_movements: r += '-1 ' | ||
90 | else: r += '0 ' | ||
91 | |||
92 | if 'left swing' in self.rear_movements: r += '1 ' | ||
93 | elif 'right swing' in self.rear_movements: r += '-1 ' | ||
94 | else: r += '0 ' | ||
95 | |||
96 | if 'left shift' in self.rear_movements: r += '1' | ||
97 | elif 'right shift' in self.rear_movements: r += '-1' | ||
98 | else: r += '0' | ||
99 | |||
100 | r += '\n' | ||
101 | |||
102 | notes = [] | ||
103 | if self.description: | ||
104 | notes.append(self.description) | ||
105 | if self.date: | ||
106 | notes.append(str(self.date.date())) | ||
107 | if self.description or self.date: | ||
108 | notes.append('') | ||
109 | notes += self.comments.split('\n') | ||
110 | |||
111 | r += ' [ ' | ||
112 | for note in notes: | ||
113 | r += '('+note+') ' | ||
114 | r += ']\n' | ||
115 | r += 'record\n' | ||
116 | return r | ||
117 | |||
118 | def main(): | ||
119 | directory = sys.argv[1] | ||
120 | start = int(sys.argv[2]) | ||
121 | end = int(sys.argv[3]) | ||
122 | end += end%4 | ||
123 | |||
124 | files = os.listdir(directory) | ||
125 | files.sort() | ||
126 | images = {} | ||
127 | for fn in files: | ||
128 | if not (fn.lower().endswith('.jpeg') or | ||
129 | fn.lower().endswith('.jpg')): | ||
130 | continue | ||
131 | i = MyImage(os.path.join(directory,fn)) | ||
132 | if i.id: | ||
133 | images[int(i.id)] = i | ||
134 | |||
135 | code = '' | ||
136 | page = 0 | ||
137 | i = start | ||
138 | while i<end: | ||
139 | page += 1 | ||
140 | code += '%%%%Page: %s %s\n' % (page, page) | ||
141 | code += '/xpos planleft def\n' | ||
142 | code += '/ypos plantop def\n' | ||
143 | |||
144 | code += 'planleft plantop\n' | ||
145 | if images.has_key(i): image = images[i] | ||
146 | else: image = MyImage(None) | ||
147 | code += image.render() | ||
148 | i += 1 | ||
149 | |||
150 | code += 'planleft planwidth add plantop\n' | ||
151 | if images.has_key(i): image = images[i] | ||
152 | else: image = MyImage(None) | ||
153 | code += image.render() | ||
154 | i += 1 | ||
155 | |||
156 | code += 'planleft plantop 5 in sub\n' | ||
157 | if images.has_key(i): image = images[i] | ||
158 | else: image = MyImage(None) | ||
159 | code += image.render() | ||
160 | i += 1 | ||
161 | |||
162 | code += 'planleft planwidth add plantop 5 in sub\n' | ||
163 | if images.has_key(i): image = images[i] | ||
164 | else: image = MyImage(None) | ||
165 | code += image.render() | ||
166 | i += 1 | ||
167 | |||
168 | code += 'showpage\n' | ||
169 | |||
170 | print lfrecord.program % dict(pages=page, code=code) | ||
171 | |||
172 | if __name__=='__main__': | ||
173 | if len(sys.argv) != 4: | ||
174 | print "Usage: %s PATH START END" % sys.argv[0] | ||
175 | |||
176 | print "Produce a sheet of four ExiFilm image records." | ||
177 | |||
178 | print " PATH is a directory with JPEG files to edit." | ||
179 | |||
180 | print " START and END are image IDs as set by ExiFilm. A series" | ||
181 | print " of PostScript pages will be generated that contain the" | ||
182 | print " images ranging from START to END." | ||
183 | |||
184 | print "Output goes to standard out." | ||
185 | else: | ||
186 | main() | ||
187 | |||