more column work

- removed sort area; users can click on columns to sort now
- displayed columns are now loaded/saved from deck
This commit is contained in:
Damien Elmes 2011-04-12 02:02:07 +09:00
parent 4b1d377a40
commit 82be9a432e
4 changed files with 101 additions and 123 deletions

View file

@ -36,7 +36,8 @@ class DeckModel(QAbstractTableModel):
self.browser = browser self.browser = browser
self.deck = browser.deck self.deck = browser.deck
self.sortKey = None self.sortKey = None
self.columns = ["question", "answer", "sortField", "cardDue", "cardEase"] self.activeCols = self.deck.conf.get(
"activeCols", ["factFld", "answer", "cardDue", "cardEase"])
self.cards = [] self.cards = []
self.cardObjs = {} self.cardObjs = {}
@ -53,7 +54,7 @@ class DeckModel(QAbstractTableModel):
return len(self.cards) return len(self.cards)
def columnCount(self, index): def columnCount(self, index):
return len(self.columns) return len(self.activeCols)
def data(self, index, role): def data(self, index, role):
if not index.isValid(): if not index.isValid():
@ -77,12 +78,7 @@ class DeckModel(QAbstractTableModel):
return QVariant() return QVariant()
elif role == Qt.DisplayRole: elif role == Qt.DisplayRole:
type = self.columnType(section) type = self.columnType(section)
if type == "question": for stype, name in self.browser.columns:
txt = _("Question")
elif type == "answer":
txt = _("Answer")
else:
for stype, name in self.browser.sortTypes:
if type == stype: if type == stype:
txt = name txt = name
break break
@ -117,11 +113,7 @@ class DeckModel(QAbstractTableModel):
###################################################################### ######################################################################
def columnType(self, column): def columnType(self, column):
type = self.columns[column] type = self.activeCols[column]
if type == "sortField":
type = self.deck.conf['sortType']
if type == "factFld":
type = "cardDue"
return type return type
def columnData(self, index): def columnData(self, index):
@ -133,7 +125,10 @@ class DeckModel(QAbstractTableModel):
return self.formatQA(c.q()) return self.formatQA(c.q())
elif type == "answer": elif type == "answer":
return self.formatQA(c.a()) return self.formatQA(c.a())
elif type == "factFld" or type == "cardDue": elif type == "factFld":
f = c.fact()
return self.formatQA(f._fields[f.model().sortIdx()])
elif type == "cardDue":
return self.nextDue(c, index) return self.nextDue(c, index)
elif type == "factCrt": elif type == "factCrt":
return time.strftime("%Y-%m-%d", time.localtime(c.fact().crt)) return time.strftime("%Y-%m-%d", time.localtime(c.fact().crt))
@ -233,7 +228,7 @@ class Browser(QMainWindow):
restoreSplitter(self.form.splitter_3, "editor3") restoreSplitter(self.form.splitter_3, "editor3")
self.form.splitter_2.setChildrenCollapsible(False) self.form.splitter_2.setChildrenCollapsible(False)
self.form.splitter_3.setChildrenCollapsible(False) self.form.splitter_3.setChildrenCollapsible(False)
self.setupSort() self.setupColumns()
self.setupToolbar() self.setupToolbar()
self.setupTable() self.setupTable()
self.setupMenus() self.setupMenus()
@ -243,7 +238,6 @@ class Browser(QMainWindow):
self.setupHooks() self.setupHooks()
self.setupEditor() self.setupEditor()
self.setupCardInfo() self.setupCardInfo()
self.updateSortIcon()
self.updateFont() self.updateFont()
self.form.searchEdit.setFocus() self.form.searchEdit.setFocus()
self.updateFilterLabel() self.updateFilterLabel()
@ -310,6 +304,7 @@ class Browser(QMainWindow):
saveGeom(self, "editor") saveGeom(self, "editor")
saveState(self, "editor") saveState(self, "editor")
saveHeader(self.form.tableView.horizontalHeader(), "editor") saveHeader(self.form.tableView.horizontalHeader(), "editor")
self.deck.conf['activeCols'] = self.model.activeCols
self.hide() self.hide()
aqt.dialogs.close("Browser") aqt.dialogs.close("Browser")
self.teardownHooks() self.teardownHooks()
@ -320,6 +315,21 @@ class Browser(QMainWindow):
if evt.key() in (Qt.Key_Escape,): if evt.key() in (Qt.Key_Escape,):
self.close() self.close()
def setupColumns(self):
self.columns = [
('question', _("Question")),
('answer', _("Answer")),
('factFld', _("Sort Field")),
('factCrt', _("Creation date")),
('factMod', _("Edit date")),
('cardMod', _("Review date")),
('cardDue', _("Due date")),
('cardIvl', _("Card interval")),
('cardEase', _("Ease factor")),
('cardReps', _("Review count")),
('cardLapses', _("Lapse count")),
]
# Searching # Searching
###################################################################### ######################################################################
@ -369,7 +379,7 @@ class Browser(QMainWindow):
def setupTable(self): def setupTable(self):
self.model = DeckModel(self) self.model = DeckModel(self)
self.form.tableView.setSortingEnabled(False) self.form.tableView.setSortingEnabled(True)
self.form.tableView.setShowGrid(False) self.form.tableView.setShowGrid(False)
self.form.tableView.setModel(self.model) self.form.tableView.setModel(self.model)
self.form.tableView.selectionModel() self.form.tableView.selectionModel()
@ -397,7 +407,6 @@ class Browser(QMainWindow):
return -1 return -1
def focusCard(self): def focusCard(self):
print "focus"
if self.card: if self.card:
try: try:
self.card.id self.card.id
@ -414,7 +423,7 @@ class Browser(QMainWindow):
return True return True
return False return False
# Headers # Headers & sorting
###################################################################### ######################################################################
def setupHeaders(self): def setupHeaders(self):
@ -424,80 +433,76 @@ class Browser(QMainWindow):
vh.hide() vh.hide()
hh.show() hh.show()
restoreHeader(hh, "editor") restoreHeader(hh, "editor")
for i in range(2): hh.setHighlightSections(False)
hh.setResizeMode(i, QHeaderView.Stretch) hh.setMinimumSectionSize(50)
hh.setResizeMode(2, QHeaderView.Interactive) self.setColumnSizes()
hh.setContextMenuPolicy(Qt.CustomContextMenu) hh.setContextMenuPolicy(Qt.CustomContextMenu)
hh.connect(hh, SIGNAL("customContextMenuRequested(QPoint)"), hh.connect(hh, SIGNAL("customContextMenuRequested(QPoint)"),
self.onHeaderContext) self.onHeaderContext)
hh.connect(hh, SIGNAL("sortIndicatorChanged(int, Qt::SortOrder)"),
self.onSortChanged)
self.setSortIndicator()
def onSortChanged(self, idx, ord):
type = self.model.activeCols[idx]
if type in ("question", "answer"):
type = "factFld"
if self.deck.conf['sortType'] != type:
self.deck.conf['sortType'] = type
# default to descending for non-text fields
if type not in ("question", "answer", "factFld"):
ord = not ord
self.deck.conf['sortBackwards'] = ord
self.model.showMatching()
# fixme: we do this in various locations
self.updateFilterLabel()
self.focusCard()
else:
self.deck.conf['sortBackwards'] = ord
self.model.cards.reverse()
self.setSortIndicator()
self.model.reset()
def setSortIndicator(self):
hh = self.form.tableView.horizontalHeader()
type = self.deck.conf['sortType']
if type not in self.model.activeCols:
hh.setSortIndicatorShown(False)
return
idx = self.model.activeCols.index(type)
if self.deck.conf['sortBackwards']:
ord = Qt.DescendingOrder
else:
ord = Qt.AscendingOrder
hh.setSortIndicator(idx, ord)
hh.setSortIndicatorShown(True)
def onHeaderContext(self, pos): def onHeaderContext(self, pos):
gpos = self.form.tableView.mapToGlobal(pos) gpos = self.form.tableView.mapToGlobal(pos)
m = QMenu() m = QMenu()
for type, name in [("question", _("Question")), for type, name in self.columns:
("answer", _("Answer")),
("sortField", _("Current Sort Field"))
] + self.sortTypes:
a = m.addAction(name) a = m.addAction(name)
a.setCheckable(True) a.setCheckable(True)
a.setChecked(type in self.model.columns) a.setChecked(type in self.model.activeCols)
a.connect(a, SIGNAL("toggled(bool)"), a.connect(a, SIGNAL("toggled(bool)"),
lambda b, t=type: self.toggleField(t)) lambda b, t=type: self.toggleField(t))
m.exec_(gpos) m.exec_(gpos)
def toggleField(self, type): def toggleField(self, type):
if type in self.model.columns: if type in self.model.activeCols:
self.model.columns.remove(type) self.model.activeCols.remove(type)
else: else:
self.model.columns.append(type) self.model.activeCols.append(type)
self.setColumnSizes()
self.model.reset() self.model.reset()
# Sorting def setColumnSizes(self):
###################################################################### hh = self.form.tableView.horizontalHeader()
for c, i in enumerate(self.model.activeCols):
def setupSort(self): if i in ("question", "answer", "factFld"):
self.sortTypes = [ hh.setResizeMode(c, QHeaderView.Stretch)
('factFld', _("Fields")),
('factCrt', _("Creation date")),
('factMod', _("Edit date")),
('cardMod', _("Review date")),
('cardDue', _("Due date")),
('cardIvl', _("Card interval")),
('cardEase', _("Ease factor")),
('cardReps', _("Review count")),
('cardLapses', _("Lapse count")),
]
for c, (type, name) in enumerate(self.sortTypes):
self.form.sortBox.addItem(name)
if type == self.deck.conf['sortType']:
idx = c
self.form.sortBox.setCurrentIndex(idx)
self.connect(self.form.sortBox, SIGNAL("activated(int)"),
self.sortChanged)
self.sortChanged(idx, refresh=False)
self.connect(self.form.sortOrder, SIGNAL("clicked()"),
self.toggleSortOrder)
def toggleSortOrder(self):
self.deck.conf['sortBackwards'] = not self.deck.conf['sortBackwards']
self.model.cards.reverse()
self.model.reset()
self.focusCard()
self.updateSortIcon()
def updateSortIcon(self):
if self.deck.conf['sortBackwards']:
self.form.sortOrder.setIcon(QIcon(":/icons/view-sort-descending.png"))
else: else:
self.form.sortOrder.setIcon(QIcon(":/icons/view-sort-ascending.png")) hh.setResizeMode(c, QHeaderView.Interactive)
def sortChanged(self, idx, refresh=True):
self.deck.conf['sortType'] = self.sortTypes[idx][0]
if refresh:
self.model.showMatching()
# fixme: we do this in various locations
self.updateFilterLabel()
self.focusCard()
# Filter tree # Filter tree
###################################################################### ######################################################################

View file

@ -164,7 +164,7 @@ title="%s">%s</button>''' % (
self.form.centralwidget.setLayout(self.mainLayout) self.form.centralwidget.setLayout(self.mainLayout)
addHook("undoEnd", self.maybeEnableUndo) addHook("undoEnd", self.maybeEnableUndo)
if self.config['mainWindowState']: if self.config['mainWindowState']:
restoreGeom(self, "mainWindow", 21) restoreGeom(self, "mainWindow")
restoreState(self, "mainWindow") restoreState(self, "mainWindow")
else: else:
self.resize(500, 400) self.resize(500, 400)

View file

@ -234,13 +234,13 @@ def restoreGeom(widget, key, offset=None):
key += "Geom" key += "Geom"
if aqt.mw.config.get(key): if aqt.mw.config.get(key):
widget.restoreGeometry(aqt.mw.config[key]) widget.restoreGeometry(aqt.mw.config[key])
# if sys.platform.startswith("darwin") and offset: if sys.platform.startswith("darwin") and offset:
# from aqt.main import QtConfig as q from aqt.main import QtConfig as q
# minor = (q.qt_version & 0x00ff00) >> 8 minor = (q.qt_version & 0x00ff00) >> 8
# if minor > 6: if minor > 6:
# # bug in osx toolkit # bug in osx toolkit
# s = widget.size() s = widget.size()
# widget.resize(s.width(), s.height()+offset*2) widget.resize(s.width(), s.height()+offset*2)
def saveState(widget, key): def saveState(widget, key):
key += "State" key += "State"

View file

@ -88,39 +88,6 @@
</property> </property>
</widget> </widget>
</item> </item>
<item row="0" column="2">
<widget class="QLabel" name="label_3">
<property name="text">
<string>Sort:</string>
</property>
</widget>
</item>
<item row="0" column="3">
<widget class="QPushButton" name="sortOrder">
<property name="maximumSize">
<size>
<width>20</width>
<height>20</height>
</size>
</property>
<property name="focusPolicy">
<enum>Qt::NoFocus</enum>
</property>
<property name="text">
<string/>
</property>
<property name="icon">
<iconset resource="icons.qrc">
<normaloff>:/icons/view-sort-ascending.png</normaloff>:/icons/view-sort-ascending.png</iconset>
</property>
<property name="flat">
<bool>true</bool>
</property>
</widget>
</item>
<item row="0" column="4">
<widget class="QComboBox" name="sortBox"/>
</item>
</layout> </layout>
</item> </item>
<item> <item>
@ -159,15 +126,21 @@
<property name="selectionBehavior"> <property name="selectionBehavior">
<enum>QAbstractItemView::SelectRows</enum> <enum>QAbstractItemView::SelectRows</enum>
</property> </property>
<attribute name="horizontalHeaderHighlightSections">
<bool>false</bool>
</attribute>
<attribute name="horizontalHeaderMinimumSectionSize">
<number>20</number>
</attribute>
<attribute name="horizontalHeaderShowSortIndicator" stdset="0">
<bool>true</bool>
</attribute>
</widget> </widget>
<widget class="QWidget" name="lowerWidget"> <widget class="QWidget" name="lowerWidget">
<layout class="QHBoxLayout" name="horizontalLayout2"> <layout class="QHBoxLayout" name="horizontalLayout2">
<property name="spacing"> <property name="spacing">
<number>0</number> <number>0</number>
</property> </property>
<property name="margin">
<number>0</number>
</property>
<item> <item>
<widget class="QWidget" name="fieldsArea" native="true"> <widget class="QWidget" name="fieldsArea" native="true">
<property name="sizePolicy"> <property name="sizePolicy">