added missing files
[swftools.git] / wx / lib / document.py
1 #!/usr/bin/env python
2 # -*- coding: UTF-8 -*-
3 #
4 # gpdf2swf.py
5 # graphical user interface for pdf2swf
6 #
7 # Part of the swftools package.
8
9 # Copyright (c) 2008,2009 Matthias Kramm <kramm@quiss.org> 
10 #
11 # This program is free software; you can redistribute it and/or modify
12 # it under the terms of the GNU General Public License as published by
13 # the Free Software Foundation; either version 2 of the License, or
14 # (at your option) any later version.
15 #
16 # This program is distributed in the hope that it will be useful,
17 # but WITHOUT ANY WARRANTY; without even the implied warranty of
18 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19 # GNU General Public License for more details.
20 #
21 # You should have received a copy of the GNU General Public License
22 # along with this program; if not, write to the Free Software
23 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
24
25 from __future__ import division
26 import os
27 import time
28 import thread
29 import gfx
30 import wx
31 from wx.lib.pubsub import Publisher
32 from subprocess import Popen, PIPE
33
34 class _SaveSWFThread:
35     def __init__(self, pdffilename, filename, one_page_per_file, doc, pages, options):
36         #self.__doc = doc
37         self.__filename = filename
38         self.__pdffilename = pdffilename
39         self.__pages = pages or range(1, doc.pages+1)
40         self.__options = options
41         self.__one_page_per_file = one_page_per_file
42
43     def Start(self):
44         self.__keep_running = self.__running = True
45         thread.start_new_thread(self.Run, ())
46         #self.Run()
47
48     def Stop(self):
49         self.__keep_running = False
50
51     def IsRunning(self):
52         return self.__running
53
54     def Run(self):
55         swf = gfx.SWF()
56
57         try:
58             plugin = self.__options.viewers.init(swf, self.__filename)
59         except Exception, e:
60             wx.CallAfter(Publisher.sendMessage, "PLUGIN_ERROR")
61             self.__running = False
62             return
63
64         if self.__one_page_per_file and not plugin.one_page_per_file:
65             wx.CallAfter(Publisher.sendMessage,
66                          "PLUGIN_ONE_PAGE_PER_FILE_NOT_SUPPORTED",
67                          {'plugin': plugin,})
68             self.__running = False
69             return
70
71         pages = len(self.__pages)
72         wx.CallAfter(Publisher.sendMessage, "SWF_BEGIN_SAVE",
73                                             {'pages': pages,})
74
75         time.sleep(0.05)
76
77         self.setparameters(gfx)
78         self.__doc = gfx.open("pdf", self.__pdffilename)
79
80         self.setparameters(swf)
81
82         try:
83             plugin.before_render()
84         except Exception, e:
85             wx.CallAfter(Publisher.sendMessage, "PLUGIN_ERROR")
86             self.__running = False
87             return
88
89         for pagenr in self.__pages:
90             page = self.__doc.getPage(pagenr)
91             swf.startpage(page.width, page.height)
92             page.render(swf)
93             swf.endpage()
94             wx.CallAfter(Publisher.sendMessage, "SWF_PAGE_SAVED",
95                                                 {'pagenr': pagenr,
96                                                  'pages': pages,})
97             time.sleep(0.05)
98
99             if self.__one_page_per_file:
100                 form = '.%%0%dd.swf' % len(str(len(self.__pages)))
101                 filename = self.__filename.replace('.swf', form % pagenr)
102                 swf.save(filename)
103                 swf = gfx.SWF()
104                 self.setparameters(swf)
105
106             if not self.__keep_running:
107                 break
108         else:
109             # This will not run if we break the for loop
110             if not self.__one_page_per_file:
111                 try:
112                     plugin.before_save(page)
113                 except Exception, e:
114                     wx.CallAfter(Publisher.sendMessage, "PLUGIN_ERROR")
115                     self.__running = False
116                     return
117                 swf.save(self.__filename)
118                 try:
119                     plugin.after_save(page)
120                 except Exception, e:
121                     wx.CallAfter(Publisher.sendMessage, "PLUGIN_ERROR")
122                     self.__running = False
123                     return
124
125         # No need. But to be sure that it's clean up
126         # as soon as possible
127         del swf
128
129         wx.CallAfter(Publisher.sendMessage, "SWF_FILE_SAVED")
130         time.sleep(0.05)
131
132         self.__running = False
133
134     def setparameters(self, swf):
135         #print "driver", swf
136         for opt in self.__options.quality:
137             if type(opt.name) in (tuple, list):
138                 for name, value in (
139                     # Example to better understand the list comprehension:
140                     # opt.name = ['a', 'b', 'c']
141                     # opt.value = [1, 2, 3]
142                     # zip them = [('a',1), ('b', 2), ('c', 3)]
143                     # pair will be in this example ('a', 1) due to
144                     # the if pair[1] condition
145                     pair for pair in zip(opt.name, opt.value) #if pair[1] == 1
146                 ):
147                     #print "1.swf.setparameter(%s, %s)" % (name, value)
148                     swf.setparameter(str(name), str(value))
149             else:
150                 #print "2.swf.setparameter(%s, %s)" % (opt.name, str(opt.value))
151                 swf.setparameter(opt.name, str(opt.value))
152
153         #swf.setparameter('noclips', '1')
154         #swf.setparameter('reordertags', '1')
155         #swf.setparameter('animate', '1')
156
157 PDF_INFO = [
158     "title", "subject", "keywords", "author",
159     "creator", "producer", "creationdate", "moddate",
160     "linearized", "tagged", "encrypted", "oktoprint",
161     "oktocopy", "oktochange", "oktoaddnotes", "version",
162 ]
163
164 class Document(object):
165     def __init__(self):
166         self.__page = None
167         self.__zoom = 1
168         self.__lastsavefile = "output.swf"
169         self.__pdffilename = None
170         self.__preview_parameters = []
171
172     def __getattr__(self, name):
173         if name in PDF_INFO:
174             return self.__pdf.getInfo(name) or "n/a"
175         raise AttributeError, name
176
177     def filename(self):
178         return self.__pdffilename
179     filename = property(filename)
180
181     def __get_lastsavefile(self):
182         return self.__lastsavefile
183     def __set_lastsavefile(self, lastsavefile):
184         self.__lastsavefile = lastsavefile
185     lastsavefile = property(__get_lastsavefile, __set_lastsavefile)
186
187     def __SwapExtension(self, filename, newext):
188         basename, ext = os.path.splitext(filename)
189         return "%s.%s" % (basename, newext)
190
191     def __Reload(self):
192         Publisher.sendMessage("PAGE_CHANGED",
193                               {'page': self.__page,
194                                'width': int(self.__page.width * self.__zoom),
195                                'height': int(self.__page.height * self.__zoom)})
196
197     def __get_preview_parameters(self):
198         return self.__preview_parameters
199     def __set_preview_parameters(self, parameters):
200         self.__preview_parameters = parameters
201     preview_parameters = property(__get_preview_parameters,
202                                   __set_preview_parameters)
203
204     def Load(self, filename):
205         self.__lastsavefile = self.__SwapExtension(filename, "swf")
206         self.__pdffilename = filename
207
208         #print 'Load',self.__preview_parameters
209         for parameter, value in self.__preview_parameters:
210             gfx.setparameter(parameter, value)
211
212         try:
213             self.__pdf = gfx.open("pdf", filename)
214         except:
215             Publisher.sendMessage("FILE_NOT_LOADED", {'filename': filename})
216         else:
217             Publisher.sendMessage("FILE_LOADED", {'pages': self.__pdf.pages})
218
219     def ChangePage(self, pagenr=1, size=None):
220         self.__page = page = self.__pdf.getPage(pagenr)
221         self.__Reload()
222
223     def Fit(self, size):
224         w = size[0] / self.__page.width
225         h = size[1] / self.__page.height
226         self.__zoom = min(w, h)
227         self.__Reload()
228
229     def Zoom(self, zoom):
230         if zoom == 1:
231             self.__zoom = 1
232         else:
233             self.__zoom += zoom
234         self.__Reload()
235
236     def GetThumbnails(self):
237         for pagenr in range(1, self.__pdf.pages + 1):
238             page = self.__pdf.getPage(pagenr)
239             yield page
240
241     def SaveSWF(self, filename, one_page_per_file, pages, options):
242         self.__lastsavefile = filename
243         t = _SaveSWFThread(self.__pdffilename, filename, one_page_per_file, self.__pdf, pages, options)
244         t.Start()
245         return t
246         
247