PyXR

c:\projects\bitpim\src \ media_root.py



0001 ### BITPIM
0002 ###
0003 ### Copyright (C) 2006 Simon Capper <scapper@sbcglobal.net>
0004 ###
0005 ### This program is free software; you can redistribute it and/or modify
0006 ### it under the terms of the BitPim license as detailed in the LICENSE file.
0007 ###
0008 
0009 
0010 # standard modules
0011 from __future__ import with_statement
0012 import contextlib
0013 import os
0014 import cStringIO
0015 import copy
0016 import sha
0017 import time
0018 import string
0019 import zipfile
0020 
0021 
0022 # wx modules
0023 import wx
0024 
0025 # BitPim modules
0026 import database
0027 import common
0028 import guiwidgets
0029 import guihelper
0030 import pubsub
0031 import widgets
0032 import wallpaper
0033 import ringers
0034 
0035 class MediaWidget(wx.Panel, widgets.BitPimWidget):
0036     def __init__(self, mainwindow, parent):
0037         super(MediaWidget, self).__init__(parent, -1)
0038         self._main_window=mainwindow
0039         self.call_history_tree_nodes={}
0040         self._parent=parent
0041         # main box sizer
0042         self.vbs=wx.BoxSizer(wx.VERTICAL)
0043         # main stats display
0044         self.vbs.Add(wx.StaticText(self, -1, 'Media summary'), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0045         # all done
0046         self.SetSizer(self.vbs)
0047         self.SetAutoLayout(True)
0048         self.vbs.Fit(self)
0049         self.ringernodes={}
0050         self.wallpapernodes={}
0051         self.widget_to_save=None
0052         self.origin_to_save=""
0053         self.SetBackgroundColour(wx.WHITE)
0054         self.ringerwidget=ringers.RingerView(self._main_window, parent, self)
0055         self.wallpaperwidget=wallpaper.WallpaperView(self._main_window, parent, self)
0056         pubsub.subscribe(self.OnPhoneModelChanged, pubsub.PHONE_MODEL_CHANGED)
0057         # populate data
0058         #self._populate()
0059 
0060     def DoMediaSummary(self):
0061         summary=[]
0062         summary=self.GetWidgetSummary(self.ringerwidget, summary)
0063         summary=self.GetWidgetSummary(self.wallpaperwidget, summary)
0064         self.vbs.Clear(deleteWindows=True)
0065         self.vbs.Add(wx.StaticText(self, -1, 'Media summary'), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0066         hbs=wx.BoxSizer(wx.HORIZONTAL)
0067         name=wx.BoxSizer(wx.VERTICAL)
0068         count=wx.BoxSizer(wx.VERTICAL)
0069         size=wx.BoxSizer(wx.VERTICAL)
0070         name.Add(wx.StaticText(self, -1, 'Origin'), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0071         count.Add(wx.StaticText(self, -1, 'Number Files'), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0072         size.Add(wx.StaticText(self, -1, 'Size'), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0073         total_files=0
0074         total_size=0
0075         for entry in summary:
0076             name.Add(wx.StaticText(self, -1, entry[0]), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0077             count.Add(wx.StaticText(self, -1, str(entry[1])), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0078             size.Add(wx.StaticText(self, -1, self.GetNiceSizeString(entry[2])), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0079             total_files+=entry[1]
0080             total_size+=entry[2]
0081         hbs.Add(name, 0, wx.ALIGN_LEFT|wx.ALL, 2) 
0082         hbs.Add(count, 0, wx.ALIGN_LEFT|wx.ALL, 2) 
0083         hbs.Add(size, 0, wx.ALIGN_LEFT|wx.ALL, 2) 
0084         self.vbs.Add(hbs,  0, wx.ALIGN_LEFT|wx.ALL, 2)
0085         self.vbs.Add(wx.StaticText(self, -1, "Total number of media files: %d" % total_files), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0086         self.vbs.Add(wx.StaticText(self, -1, "Total size of media files: %s" % self.GetNiceSizeString(total_size)), 0, wx.ALIGN_LEFT|wx.ALL, 2)
0087         self.vbs.Layout()
0088 
0089     def GetNiceSizeString(self, size):
0090         orig=size
0091         size=float(size)
0092         if size < 1024:
0093             return "%d bytes" % size
0094         size=size/1024
0095         if size < 1024:
0096             return "%.2f KB (%d bytes)" % (size, orig)
0097         size=size/1024
0098         return "%.2f MB (%d bytes)" % (size, orig)
0099 
0100     def GetWidgetSummary(self, widget, res):
0101         for k,e in widget.sections:
0102             num_files=0
0103             total_size=0
0104             for item in e:
0105                 total_size+=item.size
0106                 num_files+=1
0107             res.append((k.label, num_files, total_size))
0108         return res
0109 
0110     def GetRightClickMenuItems(self, node):
0111         result=[]
0112         result.append((widgets.BitPimWidget.MENU_NORMAL, guihelper.ID_EXPORT_MEDIA_TO_DIR, "Export to Folder ..." , "Export the media to a folder on your hard drive"))
0113         result.append((widgets.BitPimWidget.MENU_NORMAL, guihelper.ID_EXPORT_MEDIA_TO_ZIP, "Export to Zip File ..." , "Export the media to a zip file"))
0114         return result
0115 
0116     def GetRinger(self):
0117         return self.ringerwidget 
0118 
0119     def GetWallpaper(self):
0120         return self.wallpaperwidget 
0121 
0122     def OnInit(self):
0123         self.AddMediaNode("ringers", self.ringerwidget, self._tree.ringers)
0124         self.AddMediaNode("sounds", self.ringerwidget, self._tree.sounds)
0125         self.AddMediaNode("images", self.wallpaperwidget, self._tree.image)
0126         self.ringerwidget.updateprofilevariables(self._main_window.phoneprofile)
0127         self.wallpaperwidget.updateprofilevariables(self._main_window.phoneprofile)
0128         self.DoMediaSummary()
0129 
0130     def OnPhoneModelChanged(self, msg):
0131         for name in self.ringernodes:
0132             self._tree.DeletePage(self.ringernodes[name])
0133         self.ringernodes={}
0134         for name in self.wallpapernodes:
0135             self._tree.DeletePage(self.wallpapernodes[name])
0136         self.wallpapernodes={}
0137         self.OnInit()
0138         self.ringerwidget.OnRefresh()
0139         self.wallpaperwidget.OnRefresh()
0140 
0141     def SaveToDir(self, directory):
0142         if self.widget_to_save==None:
0143             self.SaveWidgetToDir(directory, self.ringerwidget)
0144             self.SaveWidgetToDir(directory, self.wallpaperwidget)
0145         else:
0146             self.SaveWidgetToDir(directory, self.widget_to_save, self.origin_to_save)
0147 
0148     def SaveWidgetToDir(self, directory, widget, filter=""):
0149         for k,e in widget.sections:
0150             # skip unrequested origins
0151             if filter!="" and filter!=k.label:
0152                 continue
0153             opath=self._main_window._fixup(os.path.join(directory, k.label))
0154             try:
0155                 os.makedirs(opath)
0156             except:
0157                 pass
0158             if not os.path.isdir(opath):
0159                 raise Exception("Unable to create export directory "+opath)
0160             for item in e:
0161                 me=widget._data[item.datakey][item.key]
0162                 if me.mediadata!=None and me.mediadata!='':
0163                     fpath=self._main_window._fixup(os.path.join(opath, me.name))
0164                     with file(fpath, "wb") as f:
0165                         f.write(me.mediadata)
0166                     if me.timestamp!=None:
0167                         os.utime(fpath, (me.timestamp, me.timestamp))
0168 
0169 
0170     def SaveToZip(self, zip_file):
0171         # create the zipfile in a buffer
0172         # and write to disk after it is all created
0173         op=cStringIO.StringIO()
0174         with contextlib.closing(zipfile.ZipFile(op, "w", zipfile.ZIP_DEFLATED)) as zip:
0175             if self.widget_to_save==None:
0176                 self.SaveWidgetToZip(zip, self.ringerwidget)
0177                 self.SaveWidgetToZip(zip, self.wallpaperwidget)
0178             else:
0179                 self.SaveWidgetToZip(zip, self.widget_to_save, self.origin_to_save)
0180         open(zip_file, "wb").write(op.getvalue())
0181 
0182     def SaveWidgetToZip(self, zip, widget, filter=""):
0183         for k,e in widget.sections:
0184             # skip unrequested origins
0185             if filter!="" and filter!=k.label:
0186                 continue
0187             for item in e:
0188                 me=widget._data[item.datakey][item.key]
0189                 if me.mediadata!=None and me.mediadata!='':
0190                     zi=zipfile.ZipInfo()
0191                     # zipfile does not like unicode. cp437 works on windows well, may be
0192                     # a better choice than ascii, but no phones currently support anything
0193                     # other than ascii for filenames
0194                     name=k.label+"/"+me.name
0195                     zi.filename=common.get_ascii_string(name, 'ignore')
0196                     if me.timestamp==None:
0197                         zi.date_time=(0,0,0,0,0,0)
0198                     else:
0199                         zi.date_time=time.localtime(me.timestamp)[:6]
0200                     zi.compress_type=zipfile.ZIP_DEFLATED
0201                     zip.writestr(zi, me.mediadata)
0202 
0203     def GetNodeList(self, widget):
0204         res=[]
0205         if widget==self.ringerwidget:
0206             for name in self.ringernodes:
0207                 res.append(name)
0208         else:
0209            for name in self.wallpapernodes:
0210                 res.append(name)
0211         res.sort()
0212         return res            
0213 
0214     def AddMediaNode(self, node_name, widget, icon=None):
0215         if widget==self.ringerwidget:
0216             if node_name not in self.ringernodes:
0217                 if icon==None:
0218                     if string.find(node_name, "sound")!=-1:
0219                         icon=self._tree.sounds
0220                     else:
0221                         icon=self._tree.ringers    
0222                 self.ringernodes[node_name]=self.AddSubPage(widget, node_name, icon)
0223         else:
0224             if node_name not in self.wallpapernodes:
0225                 if icon==None:
0226                     if string.find(node_name, "video")!=-1:
0227                         icon=self._tree.video
0228                     elif string.find(node_name, "camera")!=-1:
0229                         icon=self._tree.camera    
0230                     else:
0231                         icon=self._tree.image    
0232                 self.wallpapernodes[node_name]=self.AddSubPage(widget, node_name, icon)
0233 
0234     def GetNodeName(self, widget, node):
0235         if widget==self.ringerwidget:
0236             for name in self.ringernodes:
0237                 if self.ringernodes[name]==node:
0238                     return name
0239         else:
0240             for name in self.wallpapernodes:
0241                 if self.wallpapernodes[name]==node:
0242                     return name
0243 
0244 
0245 #------------------------------------------------------------------------------
0246 class ExportMediaToDirDialog(wx.DirDialog):
0247     def __init__(self, parent, title):
0248         super(ExportMediaToDirDialog, self).__init__(parent, message=title, style=wx.DD_DEFAULT_STYLE|wx.DD_NEW_DIR_BUTTON)
0249         self.media_root=parent.GetActiveMediaWidget()
0250 
0251     def DoDialog(self):
0252         # do export
0253         rc=self.ShowModal()
0254         if rc==wx.ID_OK:
0255             self.media_root.SaveToDir(self.GetPath())
0256 
0257 class ExportMediaToZipDialog(wx.FileDialog):
0258     def __init__(self, parent, title):
0259         self.media_root=parent.GetActiveMediaWidget()
0260         ext="Zip files (*.zip)|*.zip|All Files (*.*)|*"
0261         if self.media_root.widget_to_save!=None:
0262             default_file=self.media_root.origin_to_save+".zip"
0263             print "here 1 "+default_file
0264         else:
0265             default_file="media.zip"
0266             print "here 2 "+default_file
0267         super(ExportMediaToZipDialog, self).__init__(parent, title, defaultFile=default_file, wildcard=ext, style=wx.SAVE|wx.OVERWRITE_PROMPT|wx.CHANGE_DIR)
0268 
0269     def DoDialog(self):
0270         # do export
0271         rc=self.ShowModal()
0272         if rc==wx.ID_OK:
0273             self.media_root.SaveToZip(self.GetPath())
0274 

Generated by PyXR 0.9.4