mirror of
https://github.com/geometer/FBReaderJ.git
synced 2025-10-04 10:19:33 +02:00
labels work as other book properties
This commit is contained in:
parent
87eb3a9726
commit
6696447327
13 changed files with 148 additions and 170 deletions
|
@ -202,7 +202,7 @@ public class LibraryActivity extends TreeActivity<LibraryTree> implements MenuIt
|
||||||
if (book.File.getPhysicalFile() != null) {
|
if (book.File.getPhysicalFile() != null) {
|
||||||
menu.add(0, SHARE_BOOK_ITEM_ID, 0, resource.getResource("shareBook").getValue());
|
menu.add(0, SHARE_BOOK_ITEM_ID, 0, resource.getResource("shareBook").getValue());
|
||||||
}
|
}
|
||||||
if (myRootTree.Collection.labels(book).contains(Book.FAVORITE_LABEL)) {
|
if (book.labels().contains(Book.FAVORITE_LABEL)) {
|
||||||
menu.add(0, REMOVE_FROM_FAVORITES_ITEM_ID, 0, resource.getResource("removeFromFavorites").getValue());
|
menu.add(0, REMOVE_FROM_FAVORITES_ITEM_ID, 0, resource.getResource("removeFromFavorites").getValue());
|
||||||
} else {
|
} else {
|
||||||
menu.add(0, ADD_TO_FAVORITES_ITEM_ID, 0, resource.getResource("addToFavorites").getValue());
|
menu.add(0, ADD_TO_FAVORITES_ITEM_ID, 0, resource.getResource("addToFavorites").getValue());
|
||||||
|
@ -234,10 +234,12 @@ public class LibraryActivity extends TreeActivity<LibraryTree> implements MenuIt
|
||||||
FBUtil.shareBook(this, book);
|
FBUtil.shareBook(this, book);
|
||||||
return true;
|
return true;
|
||||||
case ADD_TO_FAVORITES_ITEM_ID:
|
case ADD_TO_FAVORITES_ITEM_ID:
|
||||||
myRootTree.Collection.setLabel(book, Book.FAVORITE_LABEL);
|
book.addLabel(Book.FAVORITE_LABEL);
|
||||||
|
myRootTree.Collection.saveBook(book, false);
|
||||||
return true;
|
return true;
|
||||||
case REMOVE_FROM_FAVORITES_ITEM_ID:
|
case REMOVE_FROM_FAVORITES_ITEM_ID:
|
||||||
myRootTree.Collection.removeLabel(book, Book.FAVORITE_LABEL);
|
book.removeLabel(Book.FAVORITE_LABEL);
|
||||||
|
myRootTree.Collection.saveBook(book, false);
|
||||||
if (getCurrentTree().onBookEvent(BookEvent.Updated, book)) {
|
if (getCurrentTree().onBookEvent(BookEvent.Updated, book)) {
|
||||||
getListAdapter().replaceAll(getCurrentTree().subTrees());
|
getListAdapter().replaceAll(getCurrentTree().subTrees());
|
||||||
getListView().invalidateViews();
|
getListView().invalidateViews();
|
||||||
|
|
|
@ -166,17 +166,6 @@ public class BookCollectionShadow extends AbstractBookCollection implements Serv
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized List<Book> booksForLabel(String label) {
|
|
||||||
if (myInterface == null) {
|
|
||||||
return Collections.emptyList();
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
return SerializerUtil.deserializeBookList(myInterface.booksForLabel(label));
|
|
||||||
} catch (RemoteException e) {
|
|
||||||
return Collections.emptyList();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public synchronized Book getRecentBook(int index) {
|
public synchronized Book getRecentBook(int index) {
|
||||||
if (myInterface == null) {
|
if (myInterface == null) {
|
||||||
return null;
|
return null;
|
||||||
|
@ -335,34 +324,6 @@ public class BookCollectionShadow extends AbstractBookCollection implements Serv
|
||||||
return Collections.emptyList();
|
return Collections.emptyList();
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized List<String> labels(Book book) {
|
|
||||||
if (myInterface != null) {
|
|
||||||
try {
|
|
||||||
return myInterface.labelsForBook(SerializerUtil.serialize(book));
|
|
||||||
} catch (RemoteException e) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Collections.emptyList();
|
|
||||||
}
|
|
||||||
|
|
||||||
public synchronized void setLabel(Book book, String label) {
|
|
||||||
if (myInterface != null) {
|
|
||||||
try {
|
|
||||||
myInterface.setLabel(SerializerUtil.serialize(book), label);
|
|
||||||
} catch (RemoteException e) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public synchronized void removeLabel(Book book, String label) {
|
|
||||||
if (myInterface != null) {
|
|
||||||
try {
|
|
||||||
myInterface.removeLabel(SerializerUtil.serialize(book), label);
|
|
||||||
} catch (RemoteException e) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public synchronized ZLTextPosition getStoredPosition(long bookId) {
|
public synchronized ZLTextPosition getStoredPosition(long bookId) {
|
||||||
if (myInterface == null) {
|
if (myInterface == null) {
|
||||||
return null;
|
return null;
|
||||||
|
|
|
@ -15,7 +15,7 @@ interface LibraryInterface {
|
||||||
int size();
|
int size();
|
||||||
List<String> books(in String query);
|
List<String> books(in String query);
|
||||||
boolean hasBooks(in String query);
|
boolean hasBooks(in String query);
|
||||||
List<String> booksForLabel(in String label);
|
|
||||||
List<String> recentBooks();
|
List<String> recentBooks();
|
||||||
|
|
||||||
String getBookByFile(in String file);
|
String getBookByFile(in String file);
|
||||||
|
@ -27,14 +27,10 @@ interface LibraryInterface {
|
||||||
boolean hasSeries();
|
boolean hasSeries();
|
||||||
List<String> series();
|
List<String> series();
|
||||||
List<String> tags();
|
List<String> tags();
|
||||||
|
List<String> labels();
|
||||||
List<String> titles(in String query);
|
List<String> titles(in String query);
|
||||||
List<String> firstTitleLetters();
|
List<String> firstTitleLetters();
|
||||||
|
|
||||||
List<String> labels();
|
|
||||||
List<String> labelsForBook(in String book);
|
|
||||||
void setLabel(in String book, in String label);
|
|
||||||
void removeLabel(in String book, in String label);
|
|
||||||
|
|
||||||
boolean saveBook(in String book, in boolean force);
|
boolean saveBook(in String book, in boolean force);
|
||||||
void removeBook(in String book, in boolean deleteFromDisk);
|
void removeBook(in String book, in boolean deleteFromDisk);
|
||||||
void addBookToRecentList(in String book);
|
void addBookToRecentList(in String book);
|
||||||
|
|
|
@ -150,10 +150,6 @@ public class LibraryService extends Service {
|
||||||
return SerializerUtil.serializeBookList(myCollection.recentBooks());
|
return SerializerUtil.serializeBookList(myCollection.recentBooks());
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<String> booksForLabel(String label) {
|
|
||||||
return SerializerUtil.serializeBookList(myCollection.booksForLabel(label));
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getRecentBook(int index) {
|
public String getRecentBook(int index) {
|
||||||
return SerializerUtil.serialize(myCollection.getRecentBook(index));
|
return SerializerUtil.serialize(myCollection.getRecentBook(index));
|
||||||
}
|
}
|
||||||
|
@ -220,18 +216,6 @@ public class LibraryService extends Service {
|
||||||
return myCollection.labels();
|
return myCollection.labels();
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<String> labelsForBook(String book) {
|
|
||||||
return myCollection.labels(SerializerUtil.deserializeBook(book));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setLabel(String book, String label) {
|
|
||||||
myCollection.setLabel(SerializerUtil.deserializeBook(book), label);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void removeLabel(String book, String label) {
|
|
||||||
myCollection.removeLabel(SerializerUtil.deserializeBook(book), label);
|
|
||||||
}
|
|
||||||
|
|
||||||
public TextPosition getStoredPosition(long bookId) {
|
public TextPosition getStoredPosition(long bookId) {
|
||||||
final ZLTextPosition position = myCollection.getStoredPosition(bookId);
|
final ZLTextPosition position = myCollection.getStoredPosition(bookId);
|
||||||
if (position == null) {
|
if (position == null) {
|
||||||
|
|
|
@ -468,6 +468,22 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
||||||
return list;
|
return list;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected List<String> listLabels(long bookId) {
|
||||||
|
final Cursor cursor = myDatabase.rawQuery(
|
||||||
|
"SELECT Labels.name FROM Labels" +
|
||||||
|
" INNER JOIN BookLabel ON BookLabel.label_id=Labels.label_id" +
|
||||||
|
" WHERE BookLabel.book_id=?",
|
||||||
|
new String[] { String.valueOf(bookId) }
|
||||||
|
);
|
||||||
|
final LinkedList<String> names = new LinkedList<String>();
|
||||||
|
while (cursor.moveToNext()) {
|
||||||
|
names.add(cursor.getString(0));
|
||||||
|
}
|
||||||
|
cursor.close();
|
||||||
|
return names;
|
||||||
|
}
|
||||||
|
|
||||||
private SQLiteStatement myDeleteBookUidsStatement;
|
private SQLiteStatement myDeleteBookUidsStatement;
|
||||||
protected void deleteAllBookUids(long bookId) {
|
protected void deleteAllBookUids(long bookId) {
|
||||||
if (myDeleteBookUidsStatement == null) {
|
if (myDeleteBookUidsStatement == null) {
|
||||||
|
@ -736,38 +752,6 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
||||||
return ids;
|
return ids;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
protected List<String> labels() {
|
|
||||||
final Cursor cursor = myDatabase.rawQuery(
|
|
||||||
"SELECT Labels.name FROM Labels" +
|
|
||||||
" INNER JOIN BookLabel ON BookLabel.label_id=Labels.label_id" +
|
|
||||||
" GROUP BY Labels.name",
|
|
||||||
null
|
|
||||||
);
|
|
||||||
final LinkedList<String> names = new LinkedList<String>();
|
|
||||||
while (cursor.moveToNext()) {
|
|
||||||
names.add(cursor.getString(0));
|
|
||||||
}
|
|
||||||
cursor.close();
|
|
||||||
return names;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected List<String> labels(long bookId) {
|
|
||||||
final Cursor cursor = myDatabase.rawQuery(
|
|
||||||
"SELECT Labels.name FROM Labels" +
|
|
||||||
" INNER JOIN BookLabel ON BookLabel.label_id=Labels.label_id" +
|
|
||||||
" WHERE BookLabel.book_id=?",
|
|
||||||
new String[] { String.valueOf(bookId) }
|
|
||||||
);
|
|
||||||
final LinkedList<String> names = new LinkedList<String>();
|
|
||||||
while (cursor.moveToNext()) {
|
|
||||||
names.add(cursor.getString(0));
|
|
||||||
}
|
|
||||||
cursor.close();
|
|
||||||
return names;
|
|
||||||
}
|
|
||||||
|
|
||||||
private SQLiteStatement mySetLabelStatement;
|
private SQLiteStatement mySetLabelStatement;
|
||||||
@Override
|
@Override
|
||||||
protected void setLabel(long bookId, String label) {
|
protected void setLabel(long bookId, String label) {
|
||||||
|
@ -797,21 +781,6 @@ final class SQLiteBooksDatabase extends BooksDatabase {
|
||||||
myRemoveLabelStatement.execute();
|
myRemoveLabelStatement.execute();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
protected List<Long> loadBooksForLabelIds(String label) {
|
|
||||||
final Cursor cursor = myDatabase.rawQuery(
|
|
||||||
"SELECT BookLabel.book_id FROM BookLabel" +
|
|
||||||
" INNER JOIN Labels ON BookLabel.label_id=Labels.label_id" +
|
|
||||||
" WHERE Labels.name=?", new String[] { label }
|
|
||||||
);
|
|
||||||
final LinkedList<Long> ids = new LinkedList<Long>();
|
|
||||||
while (cursor.moveToNext()) {
|
|
||||||
ids.add(cursor.getLong(0));
|
|
||||||
}
|
|
||||||
cursor.close();
|
|
||||||
return ids;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected List<Bookmark> loadInvisibleBookmarks(long bookId) {
|
protected List<Bookmark> loadInvisibleBookmarks(long bookId) {
|
||||||
LinkedList<Bookmark> list = new LinkedList<Bookmark>();
|
LinkedList<Bookmark> list = new LinkedList<Bookmark>();
|
||||||
|
|
|
@ -46,6 +46,7 @@ public class Book extends TitledEntity {
|
||||||
private volatile String myLanguage;
|
private volatile String myLanguage;
|
||||||
private volatile List<Author> myAuthors;
|
private volatile List<Author> myAuthors;
|
||||||
private volatile List<Tag> myTags;
|
private volatile List<Tag> myTags;
|
||||||
|
private volatile List<String> myLabels;
|
||||||
private volatile SeriesInfo mySeriesInfo;
|
private volatile SeriesInfo mySeriesInfo;
|
||||||
private volatile List<UID> myUids;
|
private volatile List<UID> myUids;
|
||||||
|
|
||||||
|
@ -81,6 +82,7 @@ public class Book extends TitledEntity {
|
||||||
myLanguage = book.myLanguage;
|
myLanguage = book.myLanguage;
|
||||||
myAuthors = book.myAuthors != null ? new ArrayList<Author>(book.myAuthors) : null;
|
myAuthors = book.myAuthors != null ? new ArrayList<Author>(book.myAuthors) : null;
|
||||||
myTags = book.myTags != null ? new ArrayList<Tag>(book.myTags) : null;
|
myTags = book.myTags != null ? new ArrayList<Tag>(book.myTags) : null;
|
||||||
|
myLabels = book.myLabels != null ? new ArrayList<String>(book.myLabels) : null;
|
||||||
mySeriesInfo = book.mySeriesInfo;
|
mySeriesInfo = book.mySeriesInfo;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -114,6 +116,7 @@ public class Book extends TitledEntity {
|
||||||
setTitle(null);
|
setTitle(null);
|
||||||
myAuthors = null;
|
myAuthors = null;
|
||||||
myTags = null;
|
myTags = null;
|
||||||
|
myLabels = null;
|
||||||
mySeriesInfo = null;
|
mySeriesInfo = null;
|
||||||
myUids = null;
|
myUids = null;
|
||||||
|
|
||||||
|
@ -140,6 +143,7 @@ public class Book extends TitledEntity {
|
||||||
void loadLists(BooksDatabase database) {
|
void loadLists(BooksDatabase database) {
|
||||||
myAuthors = database.listAuthors(myId);
|
myAuthors = database.listAuthors(myId);
|
||||||
myTags = database.listTags(myId);
|
myTags = database.listTags(myId);
|
||||||
|
myLabels = database.listLabels(myId);
|
||||||
mySeriesInfo = database.getSeriesInfo(myId);
|
mySeriesInfo = database.getSeriesInfo(myId);
|
||||||
myUids = database.listUids(myId);
|
myUids = database.listUids(myId);
|
||||||
myIsSaved = true;
|
myIsSaved = true;
|
||||||
|
@ -324,6 +328,33 @@ public class Book extends TitledEntity {
|
||||||
addTag(Tag.getTag(null, tagName));
|
addTag(Tag.getTag(null, tagName));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public List<String> labels() {
|
||||||
|
return myLabels != null ? Collections.unmodifiableList(myLabels) : Collections.<String>emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
void addLabelWithNoCheck(String label) {
|
||||||
|
if (myLabels == null) {
|
||||||
|
myLabels = new ArrayList<String>();
|
||||||
|
}
|
||||||
|
myLabels.add(label);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void addLabel(String label) {
|
||||||
|
if (myLabels == null) {
|
||||||
|
myLabels = new ArrayList<String>();
|
||||||
|
}
|
||||||
|
if (!myLabels.contains(label)) {
|
||||||
|
myLabels.add(label);
|
||||||
|
myIsSaved = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void removeLabel(String label) {
|
||||||
|
if (myLabels != null && myLabels.remove(label)) {
|
||||||
|
myIsSaved = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public List<UID> uids() {
|
public List<UID> uids() {
|
||||||
return myUids != null ? Collections.unmodifiableList(myUids) : Collections.<UID>emptyList();
|
return myUids != null ? Collections.unmodifiableList(myUids) : Collections.<UID>emptyList();
|
||||||
}
|
}
|
||||||
|
@ -414,6 +445,17 @@ public class Book extends TitledEntity {
|
||||||
for (Tag tag : tags()) {
|
for (Tag tag : tags()) {
|
||||||
database.saveBookTagInfo(myId, tag);
|
database.saveBookTagInfo(myId, tag);
|
||||||
}
|
}
|
||||||
|
final List<String> labelsInDb = database.listLabels(myId);
|
||||||
|
for (String label : labelsInDb) {
|
||||||
|
if (myLabels == null || !myLabels.contains(label)) {
|
||||||
|
database.removeLabel(myId, label);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (myLabels != null) {
|
||||||
|
for (String label : myLabels) {
|
||||||
|
database.setLabel(myId, label);
|
||||||
|
}
|
||||||
|
}
|
||||||
database.saveBookSeriesInfo(myId, mySeriesInfo);
|
database.saveBookSeriesInfo(myId, mySeriesInfo);
|
||||||
database.deleteAllBookUids(myId);
|
database.deleteAllBookUids(myId);
|
||||||
for (UID uid : uids()) {
|
for (UID uid : uids()) {
|
||||||
|
|
|
@ -264,10 +264,6 @@ public class BookCollection extends AbstractBookCollection {
|
||||||
return books(myDatabase.loadRecentBookIds());
|
return books(myDatabase.loadRecentBookIds());
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<Book> booksForLabel(String label) {
|
|
||||||
return books(myDatabase.loadBooksForLabelIds(label));
|
|
||||||
}
|
|
||||||
|
|
||||||
private List<Book> books(List<Long> ids) {
|
private List<Book> books(List<Long> ids) {
|
||||||
final List<Book> bookList = new ArrayList<Book>(ids.size());
|
final List<Book> bookList = new ArrayList<Book>(ids.size());
|
||||||
for (long id : ids) {
|
for (long id : ids) {
|
||||||
|
@ -313,6 +309,16 @@ public class BookCollection extends AbstractBookCollection {
|
||||||
return new ArrayList<Tag>(tags);
|
return new ArrayList<Tag>(tags);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public List<String> labels() {
|
||||||
|
final Set<String> labels = new HashSet<String>();
|
||||||
|
synchronized (myBooksByFile) {
|
||||||
|
for (Book book : myBooksByFile.values()) {
|
||||||
|
labels.addAll(book.labels());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return new ArrayList<String>(labels);
|
||||||
|
}
|
||||||
|
|
||||||
public boolean hasSeries() {
|
public boolean hasSeries() {
|
||||||
synchronized (myBooksByFile) {
|
synchronized (myBooksByFile) {
|
||||||
for (Book book : myBooksByFile.values()) {
|
for (Book book : myBooksByFile.values()) {
|
||||||
|
@ -366,27 +372,6 @@ public class BookCollection extends AbstractBookCollection {
|
||||||
myDatabase.saveRecentBookIds(ids);
|
myDatabase.saveRecentBookIds(ids);
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<String> labels() {
|
|
||||||
return myDatabase.labels();
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<String> labels(Book book) {
|
|
||||||
if (book == null) {
|
|
||||||
return Collections.<String>emptyList();
|
|
||||||
}
|
|
||||||
return myDatabase.labels(book.getId());
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setLabel(Book book, String label) {
|
|
||||||
myDatabase.setLabel(book.getId(), label);
|
|
||||||
fireBookEvent(BookEvent.Updated, book);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void removeLabel(Book book, String label) {
|
|
||||||
myDatabase.removeLabel(book.getId(), label);
|
|
||||||
fireBookEvent(BookEvent.Updated, book);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void setStatus(Status status) {
|
private void setStatus(Status status) {
|
||||||
myStatus = status;
|
myStatus = status;
|
||||||
fireBuildEvent(status);
|
fireBuildEvent(status);
|
||||||
|
|
|
@ -53,6 +53,7 @@ public abstract class BooksDatabase {
|
||||||
|
|
||||||
protected abstract List<Author> listAuthors(long bookId);
|
protected abstract List<Author> listAuthors(long bookId);
|
||||||
protected abstract List<Tag> listTags(long bookId);
|
protected abstract List<Tag> listTags(long bookId);
|
||||||
|
protected abstract List<String> listLabels(long bookId);
|
||||||
protected abstract SeriesInfo getSeriesInfo(long bookId);
|
protected abstract SeriesInfo getSeriesInfo(long bookId);
|
||||||
protected abstract List<UID> listUids(long bookId);
|
protected abstract List<UID> listUids(long bookId);
|
||||||
|
|
||||||
|
@ -81,9 +82,6 @@ public abstract class BooksDatabase {
|
||||||
protected abstract List<Long> loadRecentBookIds();
|
protected abstract List<Long> loadRecentBookIds();
|
||||||
protected abstract void saveRecentBookIds(final List<Long> ids);
|
protected abstract void saveRecentBookIds(final List<Long> ids);
|
||||||
|
|
||||||
protected abstract List<Long> loadBooksForLabelIds(String label);
|
|
||||||
protected abstract List<String> labels();
|
|
||||||
protected abstract List<String> labels(long bookId);
|
|
||||||
protected abstract void setLabel(long bookId, String label);
|
protected abstract void setLabel(long bookId, String label);
|
||||||
protected abstract void removeLabel(long bookId, String label);
|
protected abstract void removeLabel(long bookId, String label);
|
||||||
|
|
||||||
|
|
|
@ -58,6 +58,18 @@ public abstract class Filter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public final static class ByLabel extends Filter {
|
||||||
|
public final String Label;
|
||||||
|
|
||||||
|
public ByLabel(String label) {
|
||||||
|
Label = label;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean matches(Book book) {
|
||||||
|
return book.labels().contains(Label);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public final static class ByPattern extends Filter {
|
public final static class ByPattern extends Filter {
|
||||||
public final String Pattern;
|
public final String Pattern;
|
||||||
|
|
||||||
|
|
|
@ -55,13 +55,6 @@ public interface IBookCollection {
|
||||||
boolean hasBooks(Query query);
|
boolean hasBooks(Query query);
|
||||||
List<String> titles(Query query);
|
List<String> titles(Query query);
|
||||||
|
|
||||||
List<Book> booksForLabel(String label);
|
|
||||||
|
|
||||||
List<String> labels();
|
|
||||||
List<String> labels(Book book);
|
|
||||||
void setLabel(Book book, String label);
|
|
||||||
void removeLabel(Book book, String label);
|
|
||||||
|
|
||||||
List<Book> recentBooks();
|
List<Book> recentBooks();
|
||||||
Book getRecentBook(int index);
|
Book getRecentBook(int index);
|
||||||
void addBookToRecentList(Book book);
|
void addBookToRecentList(Book book);
|
||||||
|
@ -70,6 +63,7 @@ public interface IBookCollection {
|
||||||
Book getBookById(long id);
|
Book getBookById(long id);
|
||||||
Book getBookByUid(UID uid);
|
Book getBookByUid(UID uid);
|
||||||
|
|
||||||
|
List<String> labels();
|
||||||
List<Author> authors();
|
List<Author> authors();
|
||||||
boolean hasSeries();
|
boolean hasSeries();
|
||||||
List<String> series();
|
List<String> series();
|
||||||
|
|
|
@ -81,6 +81,11 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
params[index++] = name;
|
params[index++] = name;
|
||||||
}
|
}
|
||||||
appendTag(buffer, "filter", true, params);
|
appendTag(buffer, "filter", true, params);
|
||||||
|
} else if (filter instanceof Filter.ByLabel) {
|
||||||
|
appendTag(buffer, "filter", true,
|
||||||
|
"type", "label",
|
||||||
|
"name", ((Filter.ByLabel)filter).Label
|
||||||
|
);
|
||||||
} else if (filter instanceof Filter.BySeries) {
|
} else if (filter instanceof Filter.BySeries) {
|
||||||
appendTag(buffer, "filter", true,
|
appendTag(buffer, "filter", true,
|
||||||
"type", "series",
|
"type", "series",
|
||||||
|
@ -156,6 +161,13 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (String label : book.labels()) {
|
||||||
|
appendTag(
|
||||||
|
buffer, "label", true,
|
||||||
|
"name", label
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
final SeriesInfo seriesInfo = book.getSeriesInfo();
|
final SeriesInfo seriesInfo = book.getSeriesInfo();
|
||||||
if (seriesInfo != null) {
|
if (seriesInfo != null) {
|
||||||
appendTagWithContent(buffer, "calibre:series", seriesInfo.Series.getTitle());
|
appendTagWithContent(buffer, "calibre:series", seriesInfo.Series.getTitle());
|
||||||
|
@ -333,6 +345,7 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
private final ArrayList<UID> myUidList = new ArrayList<UID>();
|
private final ArrayList<UID> myUidList = new ArrayList<UID>();
|
||||||
private final ArrayList<Author> myAuthors = new ArrayList<Author>();
|
private final ArrayList<Author> myAuthors = new ArrayList<Author>();
|
||||||
private final ArrayList<Tag> myTags = new ArrayList<Tag>();
|
private final ArrayList<Tag> myTags = new ArrayList<Tag>();
|
||||||
|
private final ArrayList<String> myLabels = new ArrayList<String>();
|
||||||
private final StringBuilder myAuthorSortKey = new StringBuilder();
|
private final StringBuilder myAuthorSortKey = new StringBuilder();
|
||||||
private final StringBuilder myAuthorName = new StringBuilder();
|
private final StringBuilder myAuthorName = new StringBuilder();
|
||||||
private final StringBuilder mySeriesTitle = new StringBuilder();
|
private final StringBuilder mySeriesTitle = new StringBuilder();
|
||||||
|
@ -359,6 +372,7 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
myUidList.clear();
|
myUidList.clear();
|
||||||
myAuthors.clear();
|
myAuthors.clear();
|
||||||
myTags.clear();
|
myTags.clear();
|
||||||
|
myLabels.clear();
|
||||||
|
|
||||||
myState = State.READ_NOTHING;
|
myState = State.READ_NOTHING;
|
||||||
}
|
}
|
||||||
|
@ -381,6 +395,9 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
for (Tag tag : myTags) {
|
for (Tag tag : myTags) {
|
||||||
myBook.addTagWithNoCheck(tag);
|
myBook.addTagWithNoCheck(tag);
|
||||||
}
|
}
|
||||||
|
for (String label : myLabels) {
|
||||||
|
myBook.addLabelWithNoCheck(label);
|
||||||
|
}
|
||||||
for (UID uid : myUidList) {
|
for (UID uid : myUidList) {
|
||||||
myBook.addUid(uid);
|
myBook.addUid(uid);
|
||||||
}
|
}
|
||||||
|
@ -417,6 +434,11 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
if (term != null) {
|
if (term != null) {
|
||||||
myTags.add(Tag.getTag(term.split("/")));
|
myTags.add(Tag.getTag(term.split("/")));
|
||||||
}
|
}
|
||||||
|
} else if ("label".equals(localName)) {
|
||||||
|
final String name = attributes.getValue("name");
|
||||||
|
if (name != null) {
|
||||||
|
myLabels.add(name);
|
||||||
|
}
|
||||||
} else if ("series".equals(localName) && XMLNamespaces.CalibreMetadata.equals(uri)) {
|
} else if ("series".equals(localName) && XMLNamespaces.CalibreMetadata.equals(uri)) {
|
||||||
myState = State.READ_SERIES_TITLE;
|
myState = State.READ_SERIES_TITLE;
|
||||||
} else if ("series_index".equals(localName) && XMLNamespaces.CalibreMetadata.equals(uri)) {
|
} else if ("series_index".equals(localName) && XMLNamespaces.CalibreMetadata.equals(uri)) {
|
||||||
|
@ -573,6 +595,8 @@ class XMLSerializer extends AbstractSerializer {
|
||||||
names.add(n);
|
names.add(n);
|
||||||
}
|
}
|
||||||
myFilter = new Filter.ByTag(Tag.getTag(names.toArray(new String[names.size()])));
|
myFilter = new Filter.ByTag(Tag.getTag(names.toArray(new String[names.size()])));
|
||||||
|
} else if ("label".equals(type)) {
|
||||||
|
myFilter = new Filter.ByLabel(attributes.getValue("name"));
|
||||||
} else if ("series".equals(type)) {
|
} else if ("series".equals(type)) {
|
||||||
myFilter = new Filter.BySeries(new Series(
|
myFilter = new Filter.BySeries(new Series(
|
||||||
attributes.getValue("title")
|
attributes.getValue("title")
|
||||||
|
|
|
@ -19,11 +19,41 @@
|
||||||
|
|
||||||
package org.geometerplus.fbreader.library;
|
package org.geometerplus.fbreader.library;
|
||||||
|
|
||||||
|
import org.geometerplus.zlibrary.core.resources.ZLResource;
|
||||||
|
|
||||||
import org.geometerplus.fbreader.book.*;
|
import org.geometerplus.fbreader.book.*;
|
||||||
|
|
||||||
public class FavoritesTree extends FirstLevelTree {
|
public class FavoritesTree extends FilteredTree {
|
||||||
|
private final ZLResource myResource;
|
||||||
|
|
||||||
FavoritesTree(RootTree root) {
|
FavoritesTree(RootTree root) {
|
||||||
super(root, ROOT_FAVORITES);
|
super(root, new Filter.ByLabel(Book.FAVORITE_LABEL), -1);
|
||||||
|
myResource = resource().getResource(ROOT_FAVORITES);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return myResource.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getTreeTitle() {
|
||||||
|
return getSummary();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getSummary() {
|
||||||
|
return myResource.getResource("summary").getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getStringId() {
|
||||||
|
return ROOT_FAVORITES;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isSelectable() {
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -41,26 +71,7 @@ public class FavoritesTree extends FirstLevelTree {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void waitForOpening() {
|
protected boolean createSubTree(Book book) {
|
||||||
clear();
|
return createBookWithAuthorsSubTree(book);
|
||||||
for (Book book : Collection.booksForLabel(Book.FAVORITE_LABEL)) {
|
|
||||||
createBookWithAuthorsSubTree(book);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean onBookEvent(BookEvent event, Book book) {
|
|
||||||
switch (event) {
|
|
||||||
case Added:
|
|
||||||
return Collection.labels(book).contains(Book.FAVORITE_LABEL) && createBookWithAuthorsSubTree(book);
|
|
||||||
case Updated:
|
|
||||||
{
|
|
||||||
boolean changed = removeBook(book);
|
|
||||||
changed |= Collection.labels(book).contains(Book.FAVORITE_LABEL) && createBookWithAuthorsSubTree(book);
|
|
||||||
return changed;
|
|
||||||
}
|
|
||||||
case Removed:
|
|
||||||
default:
|
|
||||||
return super.onBookEvent(event, book);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -49,7 +49,7 @@ abstract class FilteredTree extends LibraryTree {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public final Status getOpeningStatus() {
|
public Status getOpeningStatus() {
|
||||||
return Status.ALWAYS_RELOAD_BEFORE_OPENING;
|
return Status.ALWAYS_RELOAD_BEFORE_OPENING;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue