Viewing file: unloadform.py (18.12 KB) -rwxr-xr-x Select action/file-type: (+) | (+) | (+) | Code (+) | Session (+) | (+) | SDB (+) | (+) | (+) | (+) | (+) | (+) |
# -*- coding: utf-8 -*- # # (c) Copyright 2001-2006 Hewlett-Packard Development Company, L.P. # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Author: Don Welch #
from base.g import * from base import utils, device, msg from prnt import cups from pcard import photocard
import sys import os, os.path import socket
from qt import *
from unloadform_base import UnloadForm_base from imagepropertiesdlg import ImagePropertiesDlg
progress_dlg = None
class IconViewItem(QIconViewItem): def __init__(self, parent, dirname, fname, path, pixmap, mime_type, mime_subtype, size, exif_info={}): QIconViewItem.__init__(self, parent, fname, pixmap) self.mime_type = mime_type self.mime_subtype = mime_subtype self.path = path self.dirname = dirname self.filename = fname self.exif_info = exif_info self.size = size self.thumbnail_set = False
class UnloadForm(UnloadForm_base): def __init__(self, bus='usb,par', device_uri=None, printer_name=None, parent=None, name=None, fl=0):
UnloadForm_base.__init__(self,parent,name,fl) self.pc = None self.device_uri = device_uri self.printer_name = printer_name self.init_failed = False
if self.device_uri and self.printer_name: log.error("You may not specify both a printer (-p) and a device (-d).") self.device_uri, self.printer_name = None, None
if not self.device_uri and not self.printer_name: probed_devices = device.probeDevices(bus=bus, filter='pcard') cups_printers = cups.getPrinters() log.debug(probed_devices) log.debug(cups_printers) max_deviceid_size, x, devices = 0, 0, {}
for d in probed_devices: if d.startswith('hp:'): printers = [] for p in cups_printers: if p.device_uri == d: printers.append(p.name) devices[x] = (d, printers) x += 1 max_deviceid_size = max(len(d), max_deviceid_size)
if x == 0: from nodevicesform import NoDevicesForm self.failure(self.__tr("<p><b>No devices found that support photo card access.</b><p>Please make sure your device is properly installed and try again.")) self.init_failed = True
elif x == 1: log.info(utils.bold("Using device: %s" % devices[0][0])) self.device_uri = devices[0][0]
else: from choosedevicedlg import ChooseDeviceDlg dlg = ChooseDeviceDlg(devices) if dlg.exec_loop() == QDialog.Accepted: self.device_uri = dlg.device_uri else: self.init_failed = True
QTimer.singleShot(0, self.initialUpdate)
def initialUpdate(self): if self.init_failed: self.cleanup(EVENT_PCARD_UNABLE_TO_MOUNT) return
QApplication.setOverrideCursor(QApplication.waitCursor) try: self.pc = photocard.PhotoCard(None, self.device_uri, self.printer_name) except Error, e: log.error("An error occured: %s" % e[0]) self.failure(self.__tr("<p><b>Unable to mount photocard.</b><p>Could not connect to device.")) self.cleanup(EVENT_PCARD_UNABLE_TO_MOUNT) return
if self.pc.device.device_uri is None and self.printer_name: log.error("Printer '%s' not found." % self.printer_name) self.failure(self.__tr("<p><b>Unable to mount photocard.</b><p>Device not found.")) self.cleanup(EVENT_PCARD_JOB_FAIL) return
if self.pc.device.device_uri is None and self.device_uri: log.error("Malformed/invalid device-uri: %s" % self.device_uri) self.failure(self.__tr("<p><b>Unable to mount photocard.</b><p>Malformed/invalid device-uri.")) self.cleanup(EVENT_PCARD_JOB_FAIL) return
try: self.pc.mount() except Error: log.error("Unable to mount photo card on device. Check that device is powered on and photo card is correctly inserted.") self.failure(self.__tr("<p><b>Unable to mount photocard.</b><p>Check that device is powered on and photo card is correctly inserted.")) self.pc.umount() self.cleanup(EVENT_PCARD_UNABLE_TO_MOUNT) return
self.pc.device.sendEvent(EVENT_START_PCARD_JOB)
disk_info = self.pc.info() self.pc.write_protect = disk_info[8]
if self.pc.write_protect: log.warning("Photo card is write protected.")
log.info("Photocard on device %s mounted" % self.pc.device_uri)
if not self.pc.write_protect: log.info("DO NOT REMOVE PHOTO CARD UNTIL YOU EXIT THIS PROGRAM")
self.unload_dir = os.path.normpath(os.path.expanduser('~')) os.chdir(self.unload_dir) self.UnloadDirectoryEdit.setText(self.unload_dir)
self.unload_list = self.pc.get_unload_list() self.DeviceText.setText(self.pc.device.device_uri)
self.image_icon_map = {'tiff' : 'tif.png', 'bmp' : 'bmp.png', 'jpeg' : 'jpg.png', 'gif' : 'gif.png', 'unknown' : 'unknown.png', } self.video_icon_map = {'unknown' : 'movie.png', 'mpeg' : 'mpg.png', }
self.total_number = 0 self.total_size = 0
self.removal_option = 0
self.UpdateStatusBar()
if self.pc.write_protect: self.FileRemovalGroup.setEnabled(False) self.LeaveAllRadio.setEnabled(False) self.RemoveSelectedRadio.setEnabled(False) self.RemoveAllRadio.setEnabled(False)
# Item map disambiguates between files of the same # name that are on the pcard in more than one location self.item_map = {} QApplication.restoreOverrideCursor()
self.load_icon_view(first_load=True)
def closeEvent(self, event): if self.pc is not None: self.pc.device.sendEvent(EVENT_END_PCARD_JOB)
event.accept()
def CancelButton_clicked(self): self.cleanup()
def cleanup(self, error=0): if self.pc is not None: if error > 0: self.pc.device.sendEvent(error, typ='error')
self.close()
def success(self): QMessageBox.information(self, self.caption(), self.__tr("<p><b>The operation completed successfully.</b>"), QMessageBox.Ok, QMessageBox.NoButton, QMessageBox.NoButton)
def failure(self, error_text): QMessageBox.critical(self, self.caption(), error_text, QMessageBox.Ok, QMessageBox.NoButton, QMessageBox.NoButton)
def load_icon_view(self, first_load): QApplication.setOverrideCursor(QApplication.waitCursor) self.first_load = first_load
if first_load: self.IconView.clear()
self.num_items = len(self.unload_list)
self.pb = QProgressBar() self.pb.setTotalSteps(self.num_items) self.statusBar().addWidget(self.pb) self.pb.show()
self.item_num = 0 self.load_timer = QTimer(self, "ScanTimer") self.connect(self.load_timer, SIGNAL('timeout()'), self.continue_load_icon_view) self.load_timer.start(0)
def continue_load_icon_view(self):
if self.item_num == self.num_items: self.load_timer.stop() self.disconnect(self.load_timer, SIGNAL('timeout()'), self.continue_load_icon_view) self.load_timer = None del self.load_timer
self.pb.hide() self.statusBar().removeWidget(self.pb)
self.IconView.adjustItems() QApplication.restoreOverrideCursor() return
f = self.unload_list[self.item_num]
self.item_num += 1 path, size = f[0], f[1]
self.pb.setProgress(self.item_num)
typ, subtyp = self.pc.classify_file(path).split('/')
if not self.first_load and typ == 'image' and subtyp == 'jpeg':
exif_info = self.pc.get_exif_path(path)
if len(exif_info) > 0:
if 'JPEGThumbnail' in exif_info: pixmap = QPixmap() pixmap.loadFromData(exif_info['JPEGThumbnail'], "JPEG")
self.resizePixmap(pixmap)
del exif_info['JPEGThumbnail'] dname, fname=os.path.split(path) x = self.item_map[fname]
if len(x) == 1: item = self.IconView.findItem(fname, 0) else: i = x.index(path) if i == 0: item = self.IconView.findItem(fname, 0) else: item = self.IconView.findItem(fname + " (%d)" % (i+1), 0)
if item is not None: item.setPixmap(pixmap) item.thumbnail_set = True
return
#elif 'TIFFThumbnail' in exif_info: # can't handle TIFF in Qt? # del exif_info['TIFFThumbnail'] # if first_load: # IconViewItem( self.IconView, filename, # QPixmap( os.path.join( prop.image_dir, 'tif.png' ) ), # typ, subtyp, size, exif_info ) # else: # pass
# continue
elif self.first_load: if typ == 'image': f = os.path.join(prop.image_dir, self.image_icon_map.get(subtyp, 'unknown.png')) elif typ == 'video': f = os.path.join(prop.image_dir, self.video_icon_map.get(subtyp, 'movie.png')) elif typ == 'audio': f = os.path.join(prop.image_dir, 'sound.png') else: f = os.path.join(prop.image_dir, 'unknown.png')
dirname, fname=os.path.split(path) num = 1 try: self.item_map[fname] except: self.item_map[fname] = [path] else: self.item_map[fname].append(path) num = len(self.item_map[fname])
if num == 1: IconViewItem(self.IconView, dirname, fname, path, QPixmap(f), typ, subtyp, size) else: IconViewItem(self.IconView, dirname, fname + " (%d)" % num, path, QPixmap(f), typ, subtyp, size)
def resizePixmap(self, pixmap): w, h = pixmap.width(), pixmap.height()
if h > 128 or w > 128: ww, hh = w - 128, h - 128 if ww >= hh: pixmap.resize(128, int(float((w-ww))/w*h)) else: pixmap.resize(int(float((h-hh))/h*w), 128)
def UpdateStatusBar(self): if self.total_number == 0: self.statusBar().message(self.__tr("No files selected")) elif self.total_number == 1: self.statusBar().message(self.__tr("1 file selected, %s" % utils.format_bytes(self.total_size, True))) else: self.statusBar().message(self.__tr("%d files selected, %s" % (self.total_number, utils.format_bytes(self.total_size, True))))
def SelectAllButton_clicked(self): self.IconView.selectAll(1)
def SelectNoneButton_clicked(self): self.IconView.selectAll(0)
def IconView_doubleClicked(self, a0): #self.Display( a0 ) pass
def UnloadDirectoryBrowseButton_clicked(self): old_dir = self.unload_dir self.unload_dir = str(QFileDialog.getExistingDirectory(self.unload_dir, self))
if not len(self.unload_dir): return elif not utils.is_path_writable(self.unload_dir): self.failure(self.__tr("<p><b>The unload directory path you entered is not valid.</b><p>The directory must exist and you must have write permissions.")) self.unload_dir = old_dir else: self.UnloadDirectoryEdit.setText(self.unload_dir) os.chdir(self.unload_dir)
def UnloadButton_clicked(self): was_cancelled = False self.unload_dir = str(self.UnloadDirectoryEdit.text()) dir_error = False
try: os.chdir(self.unload_dir) except OSError: log.error("Directory not found: %s" % self.unload_dir) dir_error = True
if dir_error or not utils.is_path_writable(self.unload_dir): self.failure(self.__tr("<p><b>The unload directory path is not valid.</b><p>Please enter a new path and try again.")) return
unload_list = [] i = self.IconView.firstItem() total_size = 0 while i is not None:
if i.isSelected(): unload_list.append((i.path, i.size, i.mime_type, i.mime_subtype)) total_size += i.size i = i.nextItem()
if total_size == 0: self.failure(self.__tr("<p><b>No files are selected to unload.</b><p>Please select one or more files to unload and try again.")) return
global progress_dlg progress_dlg = QProgressDialog(self.__tr("Unloading Files..."), self.__tr("Cancel"), total_size, self, 'progress', True) progress_dlg.setMinimumDuration(0) progress_dlg.show()
if self.removal_option == 0: total_size, total_time, was_cancelled = \ self.pc.unload(unload_list, self.UpdateUnloadProgressDlg, None, True)
elif self.removal_option == 1: # remove selected total_size, total_time, was_cancelled = \ self.pc.unload(unload_list, self.UpdateUnloadProgressDlg, None, False)
else: # remove all total_size, total_time, was_cancelled = \ self.pc.unload(unload_list, self.UpdateUnloadProgressDlg, None, False) # TODO: Remove remainder of files
progress_dlg.close()
self.pc.device.sendEvent(EVENT_PCARD_FILES_TRANSFERED)
if was_cancelled: self.failure(self.__tr("<b>Unload cancelled at user request.</b>")) else: self.success()
def UpdateUnloadProgressDlg(self, src, trg, size): global progress_dlg progress_dlg.setProgress(progress_dlg.progress() + size) progress_dlg.setLabelText(src) qApp.processEvents()
return progress_dlg.wasCancelled()
def IconView_rightButtonClicked(self, item, pos): popup = QPopupMenu(self) popup.insertItem("Properties", self.PopupProperties)
if item is not None and \ item.mime_type == 'image' and \ item.mime_subtype == 'jpeg' and \ not item.thumbnail_set:
popup.insertItem("Show Thumbnail", self.showThumbNail) popup.popup(pos)
def PopupDisplay(self): self.Display(self.IconView.currentItem())
def PopupProperties(self): self.Properties(self.IconView.currentItem())
def showThumbNail(self): item = self.IconView.currentItem() exif_info = self.pc.get_exif_path(item.path)
if len(exif_info) > 0: if 'JPEGThumbnail' in exif_info: pixmap = QPixmap() pixmap.loadFromData(exif_info['JPEGThumbnail'], "JPEG") self.resizePixmap(pixmap) del exif_info['JPEGThumbnail'] item.setPixmap(pixmap)
self.IconView.adjustItems()
else: self.failure(self.__tr("<p><b>No thumbnail found in image.</b>"))
item.thumbnail_set = True
def Display(self, item): pass # cp over file (does this even make sense to do this at this point?) # display with imagemagick?
def Properties(self, item): if item is not None: if not item.exif_info: item.exif_info = self.pc.get_exif_path(item.path)
ImagePropertiesDlg(item.filename, item.dirname, '/'.join([item.mime_type, item.mime_subtype]), utils.format_bytes(item.size, True), item.exif_info, self).exec_loop()
def IconView_selectionChanged(self): self.total_number = 0 self.total_size = 0 i = self.IconView.firstItem()
while i is not None:
if i.isSelected(): self.total_number += 1 self.total_size += i.size
i = i.nextItem()
self.UpdateStatusBar()
def IconView_clicked(self,a0,a1): pass
def IconView_clicked(self,a0): pass
def IconView_currentChanged(self,a0): pass
def FileRemovalGroup_clicked(self, a0): self.removal_option = a0
def ShowThumbnailsButton_clicked(self): self.ShowThumbnailsButton.setEnabled(False) self.load_icon_view(first_load=False)
def __tr(self,s,c = None): return qApp.translate("UnloadForm",s,c)
|