Convert gui to use datetime instead of date for all date fields.

This commit is contained in:
Charles Haley 2011-11-08 11:30:43 +01:00
parent 5944a4126d
commit 4d0a2ad7bd
8 changed files with 95 additions and 89 deletions

View file

@ -6,7 +6,7 @@
from urllib import unquote
from PyQt4.Qt import (QVariant, QFileInfo, QObject, SIGNAL, QBuffer, Qt,
QByteArray, QTranslator, QCoreApplication, QThread,
QEvent, QTimer, pyqtSignal, QDate, QDesktopServices,
QEvent, QTimer, pyqtSignal, QDateTime, QDesktopServices,
QFileDialog, QFileIconProvider, QSettings,
QIcon, QApplication, QDialog, QUrl, QFont)
@ -104,7 +104,7 @@
# }}}
NONE = QVariant() #: Null value to return from the data function of item models
UNDEFINED_QDATE = QDate(UNDEFINED_DATE)
UNDEFINED_QDATETIME = QDateTime(UNDEFINED_DATE)
ALL_COLUMNS = ['title', 'ondevice', 'authors', 'size', 'timestamp', 'rating', 'publisher',
'tags', 'series', 'pubdate']

View file

@ -7,15 +7,15 @@
from functools import partial
from PyQt4.Qt import QComboBox, QLabel, QSpinBox, QDoubleSpinBox, QDateEdit, \
QDate, QGroupBox, QVBoxLayout, QSizePolicy, \
from PyQt4.Qt import QComboBox, QLabel, QSpinBox, QDoubleSpinBox, QDateTimeEdit, \
QDateTime, QGroupBox, QVBoxLayout, QSizePolicy, \
QSpacerItem, QIcon, QCheckBox, QWidget, QHBoxLayout, SIGNAL, \
QPushButton
from calibre.utils.date import qt_to_dt, now
from calibre.gui2.complete import MultiCompleteLineEdit, MultiCompleteComboBox
from calibre.gui2.comments_editor import Editor as CommentsEditor
from calibre.gui2 import UNDEFINED_QDATE, error_dialog
from calibre.gui2 import UNDEFINED_QDATETIME, error_dialog
from calibre.utils.config import tweaks
from calibre.utils.icu import sort_key
from calibre.library.comments import comments_to_html
@ -142,27 +142,27 @@ def getter(self):
val *= 2
return val
class DateEdit(QDateEdit):
class DateTimeEdit(QDateTimeEdit):
def focusInEvent(self, x):
self.setSpecialValueText('')
QDateEdit.focusInEvent(self, x)
QDateTimeEdit.focusInEvent(self, x)
def focusOutEvent(self, x):
self.setSpecialValueText(_('Undefined'))
QDateEdit.focusOutEvent(self, x)
QDateTimeEdit.focusOutEvent(self, x)
def set_to_today(self):
self.setDate(now())
self.setDateTime(now())
def set_to_clear(self):
self.setDate(UNDEFINED_QDATE)
self.setDateTime(UNDEFINED_QDATETIME)
class DateTime(Base):
def setup_ui(self, parent):
cm = self.col_metadata
self.widgets = [QLabel('&'+cm['name']+':', parent), DateEdit(parent)]
self.widgets = [QLabel('&'+cm['name']+':', parent), DateTimeEdit(parent)]
self.widgets.append(QLabel(''))
w = QWidget(parent)
self.widgets.append(w)
@ -179,24 +179,25 @@ def setup_ui(self, parent):
w = self.widgets[1]
format = cm['display'].get('date_format','')
if not format:
format = 'dd MMM yyyy'
format = 'dd MMM yyyy hh:mm'
w.setDisplayFormat(format)
w.setCalendarPopup(True)
w.setMinimumDate(UNDEFINED_QDATE)
w.setMinimumDateTime(UNDEFINED_QDATETIME)
w.setSpecialValueText(_('Undefined'))
self.today_button.clicked.connect(w.set_to_today)
self.clear_button.clicked.connect(w.set_to_clear)
def setter(self, val):
if val is None:
val = self.widgets[1].minimumDate()
val = self.widgets[1].minimumDateTime()
else:
val = QDate(val.year, val.month, val.day)
self.widgets[1].setDate(val)
val = QDateTime(val)
self.widgets[1].setDateTime(val)
def getter(self):
val = self.widgets[1].date()
if val == UNDEFINED_QDATE:
val = self.widgets[1].dateTime()
print val
if val <= UNDEFINED_QDATETIME:
val = None
else:
val = qt_to_dt(val)
@ -537,9 +538,9 @@ def make_widgets(self, parent, main_widget_class, extra_label_text=''):
if hasattr(self.main_widget, 'valueChanged'):
# spinbox widgets
self.main_widget.valueChanged.connect(self.a_c_checkbox_changed)
if hasattr(self.main_widget, 'dateChanged'):
if hasattr(self.main_widget, 'dateTimeChanged'):
# dateEdit widgets
self.main_widget.dateChanged.connect(self.a_c_checkbox_changed)
self.main_widget.dateTimeChanged.connect(self.a_c_checkbox_changed)
def a_c_checkbox_changed(self):
if not self.ignore_change_signals:
@ -658,7 +659,7 @@ class BulkDateTime(BulkBase):
def setup_ui(self, parent):
cm = self.col_metadata
self.make_widgets(parent, DateEdit)
self.make_widgets(parent, DateTimeEdit)
self.widgets.append(QLabel(''))
w = QWidget(parent)
self.widgets.append(w)
@ -678,25 +679,26 @@ def setup_ui(self, parent):
format = 'dd MMM yyyy'
w.setDisplayFormat(format)
w.setCalendarPopup(True)
w.setMinimumDate(UNDEFINED_QDATE)
w.setMinimumDateTime(UNDEFINED_QDATETIME)
w.setSpecialValueText(_('Undefined'))
self.today_button.clicked.connect(w.set_to_today)
self.clear_button.clicked.connect(w.set_to_clear)
def setter(self, val):
if val is None:
val = self.main_widget.minimumDate()
val = self.main_widget.minimumDateTime()
else:
val = QDate(val.year, val.month, val.day)
self.main_widget.setDate(val)
val = QDateTime(val)
self.main_widget.setDateTime(val)
self.ignore_change_signals = False
def getter(self):
val = self.main_widget.date()
if val == UNDEFINED_QDATE:
val = self.main_widget.dateTime()
if val <= UNDEFINED_QDATETIME:
val = None
else:
val = qt_to_dt(val)
print val
return val
class BulkSeries(BulkBase):

View file

@ -7,14 +7,14 @@
from PyQt4.Qt import Qt, QDialog, QGridLayout, QVBoxLayout, QFont, QLabel, \
pyqtSignal, QDialogButtonBox, QInputDialog, QLineEdit, \
QDate, QCompleter
QDateTime, QCompleter
from calibre.gui2.dialogs.metadata_bulk_ui import Ui_MetadataBulkDialog
from calibre.gui2.dialogs.tag_editor import TagEditor
from calibre.ebooks.metadata import string_to_authors, authors_to_string, title_sort
from calibre.ebooks.metadata.book.base import SafeFormat
from calibre.gui2.custom_column_widgets import populate_metadata_page
from calibre.gui2 import error_dialog, ResizableDialog, UNDEFINED_QDATE, \
from calibre.gui2 import error_dialog, ResizableDialog, UNDEFINED_QDATETIME, \
gprefs, question_dialog
from calibre.gui2.progress_indicator import ProgressIndicator
from calibre.utils.config import dynamic, JSONConfig
@ -306,18 +306,21 @@ def __init__(self, window, rows, model, tab):
self.series.editTextChanged.connect(self.series_changed)
self.tag_editor_button.clicked.connect(self.tag_editor)
self.autonumber_series.stateChanged[int].connect(self.auto_number_changed)
self.pubdate.setMinimumDate(UNDEFINED_QDATE)
self.pubdate.setMinimumDateTime(UNDEFINED_QDATETIME)
pubdate_format = tweaks['gui_pubdate_display_format']
if pubdate_format is not None:
self.pubdate.setDisplayFormat(pubdate_format)
self.pubdate.setSpecialValueText(_('Undefined'))
self.clear_pubdate_button.clicked.connect(self.clear_pubdate)
self.pubdate.dateChanged.connect(self.do_apply_pubdate)
self.adddate.setDate(QDate.currentDate())
self.adddate.setMinimumDate(UNDEFINED_QDATE)
self.pubdate.dateTimeChanged.connect(self.do_apply_pubdate)
self.adddate.setDateTime(QDateTime.currentDateTime())
self.adddate.setMinimumDateTime(UNDEFINED_QDATETIME)
adddate_format = tweaks['gui_timestamp_display_format']
if adddate_format is not None:
self.adddate.setDisplayFormat(adddate_format)
self.adddate.setSpecialValueText(_('Undefined'))
self.clear_adddate_button.clicked.connect(self.clear_adddate)
self.adddate.dateChanged.connect(self.do_apply_adddate)
self.adddate.dateTimeChanged.connect(self.do_apply_adddate)
if len(self.db.custom_field_keys(include_composites=False)) == 0:
self.central_widget.removeTab(1)
@ -347,13 +350,13 @@ def do_apply_pubdate(self, *args):
self.apply_pubdate.setChecked(True)
def clear_pubdate(self, *args):
self.pubdate.setDate(UNDEFINED_QDATE)
self.pubdate.setMinimumDateTime(UNDEFINED_QDATETIME)
def do_apply_adddate(self, *args):
self.apply_adddate.setChecked(True)
def clear_adddate(self, *args):
self.adddate.setDate(UNDEFINED_QDATE)
self.adddate.setMinimumDateTime(UNDEFINED_QDATETIME)
def button_clicked(self, which):
if which == self.button_box.button(QDialogButtonBox.Apply):
@ -935,9 +938,9 @@ def accept(self):
languages = self.languages.lang_codes
pubdate = adddate = None
if self.apply_pubdate.isChecked():
pubdate = qt_to_dt(self.pubdate.date())
pubdate = qt_to_dt(self.pubdate.dateTime())
if self.apply_adddate.isChecked():
adddate = qt_to_dt(self.adddate.date())
adddate = qt_to_dt(self.adddate.dateTime())
cover_action = None
if self.cover_remove.isChecked():

View file

@ -366,7 +366,7 @@ from the value in the box</string>
<item row="9" column="1">
<layout class="QHBoxLayout" name="horizontalLayout_5">
<item>
<widget class="QDateEdit" name="adddate">
<widget class="QDateTimeEdit" name="adddate">
<property name="displayFormat">
<string>d MMM yyyy</string>
</property>
@ -411,7 +411,7 @@ from the value in the box</string>
<item row="10" column="1">
<layout class="QHBoxLayout" name="horizontalLayout_4">
<item>
<widget class="QDateEdit" name="pubdate">
<widget class="QDateTimeEdit" name="pubdate">
<property name="displayFormat">
<string>MMM yyyy</string>
</property>

View file

@ -12,9 +12,9 @@
QPen, QStyle, QPainter, QStyleOptionViewItemV4,
QIcon, QDoubleSpinBox, QVariant, QSpinBox,
QStyledItemDelegate, QComboBox, QTextDocument,
QAbstractTextDocumentLayout)
QAbstractTextDocumentLayout, QDateTime)
from calibre.gui2 import UNDEFINED_QDATE, error_dialog
from calibre.gui2 import UNDEFINED_QDATETIME, error_dialog
from calibre.gui2.widgets import EnLineEdit
from calibre.gui2.complete import MultiCompleteLineEdit, MultiCompleteComboBox
from calibre.utils.date import now, format_date
@ -107,25 +107,23 @@ def createEditor(self, parent, option, index):
class DateDelegate(QStyledItemDelegate): # {{{
def __init__(self, parent, tweak_name='gui_timestamp_display_format',
default_format='dd MMM yyyy', editor_format='dd MMM yyyy'):
default_format='dd MMM yyyy'):
QStyledItemDelegate.__init__(self, parent)
self.tweak_name = tweak_name
self.default_format = default_format
self.editor_format = editor_format
self.format = tweaks[self.tweak_name]
if self.format is None:
format = default_format
def displayText(self, val, locale):
d = val.toDate()
if d <= UNDEFINED_QDATE:
d = val.toDateTime()
if d <= UNDEFINED_QDATETIME:
return ''
format = tweaks[self.tweak_name]
if format is None:
format = self.default_format
return format_date(d.toPyDate(), format)
return format_date(d.toPyDateTime(), self.format)
def createEditor(self, parent, option, index):
qde = QStyledItemDelegate.createEditor(self, parent, option, index)
qde.setDisplayFormat(self.editor_format)
qde.setMinimumDate(UNDEFINED_QDATE)
qde.setDisplayFormat(self.format)
qde.setMinimumDateTime(UNDEFINED_QDATETIME)
qde.setSpecialValueText(_('Undefined'))
qde.setCalendarPopup(True)
return qde
@ -134,18 +132,18 @@ def createEditor(self, parent, option, index):
class PubDateDelegate(QStyledItemDelegate): # {{{
def displayText(self, val, locale):
d = val.toDate()
if d <= UNDEFINED_QDATE:
d = val.toDateTime()
if d <= UNDEFINED_QDATETIME:
return ''
format = tweaks['gui_pubdate_display_format']
if format is None:
format = 'MMM yyyy'
return format_date(d.toPyDate(), format)
self.format = tweaks['gui_pubdate_display_format']
if self.format is None:
self.format = 'MMM yyyy'
return format_date(d.toPyDateTime(), self.format)
def createEditor(self, parent, option, index):
qde = QStyledItemDelegate.createEditor(self, parent, option, index)
qde.setDisplayFormat('MM yyyy')
qde.setMinimumDate(UNDEFINED_QDATE)
qde.setDisplayFormat(self.format)
qde.setMinimumDateTime(UNDEFINED_QDATETIME)
qde.setSpecialValueText(_('Undefined'))
qde.setCalendarPopup(True)
return qde
@ -259,15 +257,15 @@ def set_format(self, format):
self.format = format
def displayText(self, val, locale):
d = val.toDate()
if d <= UNDEFINED_QDATE:
d = val.toDateTime()
if d <= UNDEFINED_QDATETIME:
return ''
return format_date(d.toPyDate(), self.format)
return format_date(d.toPyDateTime(), self.format)
def createEditor(self, parent, option, index):
qde = QStyledItemDelegate.createEditor(self, parent, option, index)
qde.setDisplayFormat(self.format)
qde.setMinimumDate(UNDEFINED_QDATE)
qde.setMinimumDateTime(UNDEFINED_QDATETIME)
qde.setSpecialValueText(_('Undefined'))
qde.setCalendarPopup(True)
return qde
@ -279,11 +277,11 @@ def setEditorData(self, editor, index):
val = m.db.data[index.row()][m.custom_columns[m.column_map[index.column()]]['rec_index']]
if val is None:
val = now()
editor.setDate(val)
editor.setDateTime(val)
def setModelData(self, editor, model, index):
val = editor.date()
if val <= UNDEFINED_QDATE:
val = editor.dateTime()
if val <= UNDEFINED_QDATETIME:
val = None
model.setData(index, QVariant(val), Qt.EditRole)

View file

@ -9,9 +9,9 @@
from collections import defaultdict
from PyQt4.Qt import (QAbstractTableModel, Qt, pyqtSignal, QIcon, QImage,
QModelIndex, QVariant, QDate, QColor)
QModelIndex, QVariant, QDateTime, QColor)
from calibre.gui2 import NONE, UNDEFINED_QDATE
from calibre.gui2 import NONE, UNDEFINED_QDATETIME
from calibre.utils.pyparsing import ParseException
from calibre.ebooks.metadata import fmt_sidx, authors_to_string, string_to_authors
from calibre.ebooks.metadata.book.base import SafeFormat
@ -580,9 +580,9 @@ def rating_type(r, idx=-1):
def datetime_type(r, idx=-1):
val = self.db.data[r][idx]
if val is not None:
return QVariant(QDate(val))
return QVariant(QDateTime(val))
else:
return QVariant(UNDEFINED_QDATE)
return QVariant(UNDEFINED_QDATETIME)
def bool_type(r, idx=-1):
return None # displayed using a decorator
@ -815,7 +815,7 @@ def set_custom_column_data(self, row, colhead, value):
if not val:
val = None
elif typ == 'datetime':
val = value.toDate()
val = value.toDateTime()
if val.isNull():
val = None
else:
@ -860,7 +860,7 @@ def setData(self, index, value, role):
if column not in self.editable_cols:
return False
val = int(value.toInt()[0]) if column == 'rating' else \
value.toDate() if column in ('timestamp', 'pubdate') else \
value.toDateTime() if column in ('timestamp', 'pubdate') else \
unicode(value.toString()).strip()
id = self.db.id(row)
books_to_refresh = set([id])

View file

@ -9,7 +9,7 @@
import textwrap, re, os, errno, shutil
from PyQt4.Qt import (Qt, QDateEdit, QDate, pyqtSignal, QMessageBox,
from PyQt4.Qt import (Qt, QDateTimeEdit, pyqtSignal, QMessageBox,
QIcon, QToolButton, QWidget, QLabel, QGridLayout, QApplication,
QDoubleSpinBox, QListWidgetItem, QSize, QPixmap, QDialog, QMenu,
QPushButton, QSpinBox, QLineEdit, QSizePolicy, QDialogButtonBox, QAction)
@ -21,7 +21,7 @@
from calibre.ebooks.metadata import (title_sort, authors_to_string,
string_to_authors, check_isbn, authors_to_sort_string)
from calibre.ebooks.metadata.meta import get_metadata
from calibre.gui2 import (file_icon_provider, UNDEFINED_QDATE,
from calibre.gui2 import (file_icon_provider, UNDEFINED_QDATETIME,
choose_files, error_dialog, choose_images)
from calibre.utils.date import (local_tz, qt_to_dt, as_local_time,
UNDEFINED_DATE)
@ -1377,25 +1377,24 @@ def commit(self, db, id_):
# }}}
class DateEdit(QDateEdit): # {{{
class DateEdit(QDateTimeEdit): # {{{
TOOLTIP = ''
LABEL = _('&Date:')
FMT = 'd MMM yyyy'
FMT = 'dd MMM yyyy hh:mm:ss'
ATTR = 'timestamp'
TWEAK = 'gui_timestamp_display_format'
def __init__(self, parent):
QDateEdit.__init__(self, parent)
QDateTimeEdit.__init__(self, parent)
self.setToolTip(self.TOOLTIP)
self.setWhatsThis(self.TOOLTIP)
fmt = self.FMT
fmt = tweaks[self.TWEAK]
if fmt is None:
fmt = tweaks['gui_pubdate_display_format']
if fmt is None:
fmt = 'MMM yyyy'
fmt = self.FMT
self.setDisplayFormat(fmt)
self.setCalendarPopup(True)
self.setMinimumDate(UNDEFINED_QDATE)
self.setMinimumDateTime(UNDEFINED_QDATETIME)
self.setSpecialValueText(_('Undefined'))
self.clear_button = QToolButton(parent)
self.clear_button.setIcon(QIcon(I('trash.png')))
@ -1408,12 +1407,12 @@ def reset_date(self, *args):
@dynamic_property
def current_val(self):
def fget(self):
return qt_to_dt(self.date(), as_utc=False)
return qt_to_dt(self.dateTime(), as_utc=False)
def fset(self, val):
if val is None:
val = UNDEFINED_DATE
val = as_local_time(val)
self.setDate(QDate(val.year, val.month, val.day))
self.setDateTime(val)
return property(fget=fget, fset=fset)
def initialize(self, db, id_):
@ -1429,11 +1428,12 @@ def commit(self, db, id_):
@property
def changed(self):
o, c = self.original_val, self.current_val
return o.year != c.year or o.month != c.month or o.day != c.day
return o != c
class PubdateEdit(DateEdit):
LABEL = _('Publishe&d:')
FMT = None
FMT = 'MMM yyyy'
ATTR = 'pubdate'
TWEAK = 'gui_pubdate_display_format'
# }}}

View file

@ -7,7 +7,7 @@
__docformat__ = 'restructuredtext en'
import re
from datetime import datetime
from datetime import datetime, time
from functools import partial
from dateutil.parser import parse
@ -161,6 +161,9 @@ def format_date(dt, format, assume_utc=False, as_utc=False):
if not format:
format = 'dd MMM yyyy'
if not isinstance(dt, datetime):
dt = datetime.combine(dt, time())
if hasattr(dt, 'tzinfo'):
if dt.tzinfo is None:
dt = dt.replace(tzinfo=_utc_tz if assume_utc else