Add "About" icon for Mac. Adjust "About" window layout. Add "Search" button to library.
[dorian] / librarydialog.cpp
1 #include <QtGui>
2 #include <QDebug>
3 #include <QFileInfo>
4 #include <QDir>
5 #include <QModelIndex>
6
7 #ifdef Q_WS_MAEMO_5
8 #include <QtMaemo5/QMaemo5InformationBox>
9 #endif
10
11 #include "librarydialog.h"
12 #include "library.h"
13 #include "sortedlibrary.h"
14 #include "book.h"
15 #include "infodialog.h"
16 #include "settings.h"
17 #include "listwindow.h"
18 #include "listview.h"
19 #include "trace.h"
20 #include "bookfinder.h"
21
22 LibraryDialog::LibraryDialog(QWidget *parent): ListWindow(parent)
23 {
24     setWindowTitle(tr("Library"));
25
26     // Add actions
27
28 #ifndef Q_WS_MAEMO_5
29     addItemAction(tr("Details"), this, SLOT(onDetails()));
30     addItemAction(tr("Read"), this, SLOT(onRead()));
31     addItemAction(tr("Delete"), this, SLOT(onRemove()));
32 #endif // ! Q_WS_MAEMO_5
33
34     addAction(tr("Add book"), this, SLOT(onAdd()), ":/icons/add.png");
35     addAction(tr("Add books from folder"), this, SLOT(onAddFolder()),
36               ":/icons/folder.png");
37     addAction(tr("Search the Web"), this, SLOT(onSearch()), ":/icons/search.png");
38
39     // Create and add list view
40     list = new ListView(this);
41     sortedLibrary = new SortedLibrary(this);
42     list->setModel(sortedLibrary);
43     list->setSelectionMode(QAbstractItemView::SingleSelection);
44     list->setSpacing(1);
45     Library *library = Library::instance();
46     QModelIndex current = library->nowReading();
47     setSelected(current);
48     addList(list);
49
50     progress = new QProgressDialog(tr("Adding books"), "", 0, 0, this);
51     progress->reset();
52     progress->setMinimumDuration(0);
53     progress->setWindowModality(Qt::WindowModal);
54     progress->setCancelButton(0);
55
56     connect(Library::instance(), SIGNAL(nowReadingChanged()),
57             this, SLOT(onCurrentBookChanged()));
58     connect(Library::instance(),
59             SIGNAL(rowsInserted(const QModelIndex &, int, int)),
60             this,
61             SLOT(onBookAdded()));
62     connect(list, SIGNAL(activated(const QModelIndex &)),
63             this, SLOT(onItemActivated(const QModelIndex &)));
64 }
65
66 void LibraryDialog::onAdd()
67 {
68     Library *library = Library::instance();
69
70     // Figure out directory to show
71     QString lastDir = Settings::instance()->value("lastdir").toString();
72     if (lastDir == "") {
73         lastDir = QDir::homePath();
74     }
75
76     // Get book file name
77     QString path = QFileDialog::getOpenFileName(this, tr("Add Book"),
78                                                 lastDir, "Books (*.epub)");
79     if (path == "") {
80         return;
81     }
82
83     // Save directory selected
84     Settings::instance()->setValue("lastdir", QFileInfo(path).absolutePath());
85
86     // Add book to library
87     QModelIndex index = library->find(path);
88     if (index.isValid()) {
89 #ifdef Q_WS_MAEMO_5
90         QMaemo5InformationBox::information(this,
91             tr("This book is already in the library"),
92             QMaemo5InformationBox::DefaultTimeout);
93 #else
94         (void)QMessageBox::information(this, tr("Dorian"),
95             tr("This book is already in the library"), QMessageBox::Ok);
96 #endif // Q_WS_MAEMO_5
97         setSelected(index);
98     }
99     else {
100         library->add(path);
101     }
102 }
103
104 void LibraryDialog::onBookAdded()
105 {
106     Library *library = Library::instance();
107     setSelected(library->index(library->rowCount() - 1));
108 }
109
110 #ifndef Q_WS_MAEMO_5
111
112 void LibraryDialog::onRemove()
113 {
114     QModelIndex current = sortedLibrary->mapToSource(list->currentIndex());
115     if (current.isValid()) {
116         Book *currentBook = Library::instance()->book(current);
117         QString title = currentBook->name();
118         if (QMessageBox::Yes ==
119             QMessageBox::question(this, tr("Delete book"),
120                 tr("Delete book \"%1\" from library?").
121                     arg(currentBook->shortName()),
122                 QMessageBox::Yes | QMessageBox::No)) {
123             Library::instance()->remove(current);
124         }
125     }
126 }
127
128 void LibraryDialog::onRead()
129 {
130     qDebug() << "LibraryDialog::onRead";
131     QModelIndex current = sortedLibrary->mapToSource(list->currentIndex());
132     if (current.isValid()) {
133         Library::instance()->setNowReading(current);
134     }
135 }
136
137 void LibraryDialog::onDetails()
138 {
139     onItemActivated(list->currentIndex());
140 }
141
142 #endif // Q_WS_MAEMO_5
143
144 void LibraryDialog::onItemActivated(const QModelIndex &index)
145 {
146     qDebug() << "LibraryDialog::onItemActivated";
147     QModelIndex libraryIndex = sortedLibrary->mapToSource(index);
148     Book *book = Library::instance()->book(libraryIndex);
149     (new InfoDialog(book, this))->exec();
150 }
151
152 QString LibraryDialog::createItemText(const Book *book)
153 {
154     QString text = book->title + "\n";
155     if (book->creators.size()) {
156         text += book->creators[0];
157         for (int i = 1; i < book->creators.size(); i++) {
158             text += ", " + book->creators[i];
159         }
160     }
161     return text;
162 }
163
164 void LibraryDialog::onCurrentBookChanged()
165 {
166     close();
167 }
168
169 void LibraryDialog::setSelected(const QModelIndex &libraryIndex)
170 {
171     QModelIndex sortedIndex = sortedLibrary->mapFromSource(libraryIndex);
172     list->selectionModel()->clearSelection();
173     if (sortedIndex.isValid()) {
174         list->selectionModel()->select(sortedIndex,
175                                        QItemSelectionModel::Select);
176         list->setCurrentIndex(sortedIndex);
177     }
178 }
179
180 QModelIndex LibraryDialog::selected() const
181 {
182     QModelIndexList selectedItems = list->selectionModel()->selectedIndexes();
183     if (selectedItems.size()) {
184         return sortedLibrary->mapToSource(selectedItems[0]);
185     }
186     return QModelIndex();
187 }
188
189 void LibraryDialog::onAddFolder()
190 {
191     Trace t("LibraryDialog::onAddFolder");
192
193     // Get folder name
194     Settings *settings = Settings::instance();
195     QString last =
196             settings->value("lastfolderadded", QDir::homePath()).toString();
197     QString path =
198             QFileDialog::getExistingDirectory(this, tr("Select folder"), last);
199     if (path == "") {
200         return;
201     }
202     settings->setValue("lastfolderadded", QFileInfo(path).absolutePath());
203     qDebug() << path;
204
205     // Add books from folder
206     progress->setWindowTitle(tr("Adding books"));
207     BookFinder *bookFinder = new BookFinder(this);
208     Library *library = Library::instance();
209     connect(bookFinder, SIGNAL(begin(int)), progress, SLOT(setMaximum(int)));
210     connect(bookFinder, SIGNAL(add(const QString &)),
211             this, SLOT(onAddFromFolder(const QString &)));
212     connect(bookFinder, SIGNAL(add(const QString &)),
213             library, SLOT(add(const QString &)));
214     connect(bookFinder, SIGNAL(done(int)),
215             this, SLOT(onAddFromFolderDone(int)));
216     bookFinder->find(path, Library::instance()->bookPaths());
217 }
218
219 void LibraryDialog::onAddFromFolderDone(int added)
220 {
221     QString msg;
222
223     switch (added) {
224     case 0: msg = tr("No new books found"); break;
225     case 1: msg = tr("One book added"); break;
226     default: msg = tr("%1 books added").arg(added);
227     }
228
229     progress->reset();
230     qDebug() << "LibraryDialog::onRefreshDone:" << msg;
231 #ifdef Q_WS_MAEMO_5
232     QMaemo5InformationBox::information(this, msg);
233 #else
234     // FIXME
235 #endif
236 }
237
238 void LibraryDialog::onAddFromFolder(const QString &path)
239 {
240     progress->setLabelText(QFileInfo(path).fileName());
241     progress->setValue(progress->value() + 1);
242 }